Jawaban:
Jika kontennya berupa string:
$someString = "Hello, World!"
$md5 = New-Object -TypeName System.Security.Cryptography.MD5CryptoServiceProvider
$utf8 = New-Object -TypeName System.Text.UTF8Encoding
$hash = [System.BitConverter]::ToString($md5.ComputeHash($utf8.GetBytes($someString)))
Jika konten adalah file:
$someFilePath = "C:\foo.txt"
$md5 = New-Object -TypeName System.Security.Cryptography.MD5CryptoServiceProvider
$hash = [System.BitConverter]::ToString($md5.ComputeHash([System.IO.File]::ReadAllBytes($someFilePath)))
Mulai di PowerShell versi 4, ini mudah dilakukan untuk file di luar kotak dengan Get-FileHash
cmdlet:
Get-FileHash <filepath> -Algorithm MD5
Ini tentu saja lebih disukai karena menghindari masalah yang ditawarkan oleh solusi pertama seperti yang diidentifikasi dalam komentar (menggunakan aliran, menutupnya, dan mendukung file besar).
Exception calling "ReadAllBytes" with "1" argument(s): "The file is too long. This operation is currently limited to supporting files less than 2 gigabytes in size."
Sebagai orang Linux yang baru mengenal Powershell, saya sangat jengkel dengan perjuangan yang saya alami untuk mendapatkan jumlah md5, yang hanya ada md5sum file.ext
di Linux.
$hash = [System.BitConverter]::ToString($md5.ComputeHash([System.IO.File]::Open("$someFilePath",[System.IO.Filemode]::Open, [System.IO.FileAccess]::Read)))
Ini memberi Anda penggunaan memori rendah dan tidak ada batas 2GB .
$stream = [System.IO.File]::Open("$someFilePath",[System.IO.Filemode]::Open, [System.IO.FileAccess]::Read)
maka $hash = [System.BitConverter]::ToString($md5.ComputeHash($stream))
kemudian$stream.Close()
Jika Anda menggunakan PowerShell Community Extensions ada commandlet Get-Hash yang akan melakukan ini dengan mudah:
C:\PS> "hello world" | Get-Hash -Algorithm MD5
Algorithm: MD5
Path :
HashString : E42B054623B3799CB71F0883900F2764
Get-FileHash
di vanilla PowerShell 4.0. Vide TechNet .
Berikut adalah dua baris, cukup ganti "halo" di baris # 2:
PS C:\> [Reflection.Assembly]::LoadWithPartialName("System.Web")
PS C:\> [System.Web.Security.FormsAuthentication]::HashPasswordForStoringInConfigFile("hello", "MD5")
Inilah fungsi yang saya gunakan yang menangani jalur relatif dan absolut:
function md5hash($path)
{
$fullPath = Resolve-Path $path
$md5 = new-object -TypeName System.Security.Cryptography.MD5CryptoServiceProvider
$file = [System.IO.File]::Open($fullPath,[System.IO.Filemode]::Open, [System.IO.FileAccess]::Read)
try {
[System.BitConverter]::ToString($md5.ComputeHash($file))
} finally {
$file.Dispose()
}
}
Terima kasih kepada @davor di atas atas saran untuk menggunakan Open () dan bukan ReadAllBytes () dan ke @ jpmc26 untuk saran untuk menggunakan blok akhirnya.
Dispose
panggilan harus berada dalam finally
blok.
Perintah bawaan lain yang telah lama diinstal di Windows secara default sejak 2003 adalah Certutil , yang tentu saja dapat dipanggil dari PowerShell juga.
CertUtil -hashfile file.foo MD5
(Peringatan: MD5 harus dalam semua batas untuk ketahanan maksimal)
FipsAlgorithmPolicy
diaktifkan.
Ada banyak contoh online menggunakan ComputeHash (). Pengujian saya menunjukkan ini sangat lambat ketika menjalankan koneksi jaringan. Cuplikan di bawah ini berjalan lebih cepat untuk saya, namun jarak tempuh Anda mungkin berbeda-beda:
$md5 = [System.Security.Cryptography.MD5]::Create("MD5")
$fd = [System.IO.File]::OpenRead($file)
$buf = New-Object byte[] (1024*1024*8) # 8 MB buffer
while (($read_len = $fd.Read($buf,0,$buf.length)) -eq $buf.length){
$total += $buf.length
$md5.TransformBlock($buf,$offset,$buf.length,$buf,$offset)
Write-Progress -Activity "Hashing File" `
-Status $file -percentComplete ($total/$fd.length * 100)
}
# Finalize the last read
$md5.TransformFinalBlock($buf, 0, $read_len)
$hash = $md5.Hash
# Convert hash bytes to a hexadecimal formatted string
$hash | foreach { $hash_txt += $_.ToString("x2") }
Write-Host $hash_txt
write-progress
telepon? Stabilo sintaks sepertinya tidak menyukainya.
Situs ini memiliki contoh: Menggunakan Powershell untuk Checksums MD5 . Ia menggunakan .NET framework untuk membuat instance dari algoritma hash MD5 untuk menghitung hash.
Berikut kode dari artikel tersebut, menggabungkan komentar Stephen:
param
(
$file
)
$algo = [System.Security.Cryptography.HashAlgorithm]::Create("MD5")
$stream = New-Object System.IO.FileStream($Path, [System.IO.FileMode]::Open,
[System.IO.FileAccess]::Read)
$md5StringBuilder = New-Object System.Text.StringBuilder
$algo.ComputeHash($stream) | % { [void] $md5StringBuilder.Append($_.ToString("x2")) }
$md5StringBuilder.ToString()
$stream.Dispose()
Sebagaimana dinyatakan dalam jawaban yang diterima, Get-FileHash
mudah digunakan dengan file, tetapi juga dimungkinkan untuk menggunakannya dengan string:
$s = "asdf"
Get-FileHash -InputStream ([System.IO.MemoryStream]::New([System.Text.Encoding]::ASCII.GetBytes($s)))
Sekarang ada fungsi Get-FileHash yang sangat berguna.
PS C:\> Get-FileHash C:\Users\Andris\Downloads\Contoso8_1_ENT.iso -Algorithm SHA384 | Format-List
Algorithm : SHA384
Hash : 20AB1C2EE19FC96A7C66E33917D191A24E3CE9DAC99DB7C786ACCE31E559144FEAFC695C58E508E2EBBC9D3C96F21FA3
Path : C:\Users\Andris\Downloads\Contoso8_1_ENT.iso
Ubah saja SHA384
ke MD5
.
Contohnya adalah dari dokumentasi resmi PowerShell 5.1 . Dokumentasi memiliki lebih banyak contoh.
Ini menjadi satu baris jika Anda mengunduh File Checksum Integrity Verifier (FCIV) dari Microsoft.
Saya mengunduh FCIV dari sini: Ketersediaan dan deskripsi utilitas Verifikasi Pemeriksaan File Checksum
Jalankan perintah berikut. Saya punya sepuluh file untuk diperiksa.
Get-ChildItem WTAM*.tar | % {.\fciv $_.Name}
PowerShell One-Liners (string ke hash)
MD5
([System.BitConverter]::ToString((New-Object -TypeName System.Security.Cryptography.MD5CryptoServiceProvider).ComputeHash((New-Object -TypeName System.Text.UTF8Encoding).GetBytes("Hello, World!")))).Replace("-","")
SHA1
([System.BitConverter]::ToString((New-Object -TypeName System.Security.Cryptography.SHA1CryptoServiceProvider).ComputeHash((New-Object -TypeName System.Text.UTF8Encoding).GetBytes("Hello, World!")))).Replace("-","")
SHA256
([System.BitConverter]::ToString((New-Object -TypeName System.Security.Cryptography.SHA256CryptoServiceProvider).ComputeHash((New-Object -TypeName System.Text.UTF8Encoding).GetBytes("Hello, World!")))).Replace("-","")
SHA384
([System.BitConverter]::ToString((New-Object -TypeName System.Security.Cryptography.SHA384CryptoServiceProvider).ComputeHash((New-Object -TypeName System.Text.UTF8Encoding).GetBytes("Hello, World!")))).Replace("-","")
SHA512
([System.BitConverter]::ToString((New-Object -TypeName System.Security.Cryptography.SHA512CryptoServiceProvider).ComputeHash((New-Object -TypeName System.Text.UTF8Encoding).GetBytes("Hello, World!")))).Replace("-","")
Ini akan mengembalikan hash MD5 untuk file di komputer jarak jauh:
Invoke-Command -ComputerName RemoteComputerName -ScriptBlock {
$fullPath = Resolve-Path 'c:\Program Files\Internet Explorer\iexplore.exe'
$md5 = new-object -TypeName System.Security.Cryptography.MD5CryptoServiceProvider
$file = [System.IO.File]::OpenRead($fullPath)
$hash = [System.BitConverter]::ToString($md5.ComputeHash($file))
$hash -replace "-", ""
$file.Dispose()
}
Ini adalah contoh cantik yang mencoba memverifikasi sidik jari SHA256. Saya mengunduh gpg4win v3.0.3 menggunakan PowerShell v4 (membutuhkan Get-FileHash
).
Unduh paket dari https://www.gpg4win.org/download.html , buka PowerShell, ambil hash dari halaman unduh, dan jalankan:
cd ${env:USERPROFILE}\Downloads
$file = "gpg4win-3.0.3.exe"
# Set $hash to the hash reference from the download page:
$hash = "477f56212ee60cc74e0c5e5cc526cec52a069abff485c89c2d57d1b4b6a54971"
# If you have an MD5 hash: # $hashAlgo="MD5"
$hashAlgo = "SHA256"
$computed_hash = (Get-FileHash -Algorithm $hashAlgo $file).Hash.ToUpper()
if ($computed_hash.CompareTo($hash.ToUpper()) -eq 0 ) {
Write-Output "Hash matches for file $file"
}
else {
Write-Output ("Hash DOES NOT match for file {0}: `nOriginal hash: {1} `nComputed hash: {2}" -f ($file, $hash.ToUpper(), $computed_hash))
}
Keluaran:
Hash matches for file gpg4win-3.0.3.exe
Berikut ini adalah contoh satu baris-perintah dengan baik menghitung checksum yang tepat dari berkas , seperti yang baru saja Anda unduh, dan membandingkannya dengan checksum asli yang diterbitkan.
Sebagai contoh, saya menulis contoh untuk mengunduh dari proyek Apache JMeter . Dalam hal ini Anda memiliki:
3a84491f10fb7b147101cf3926c4a855 * apache-jmeter-4.0.zip
Kemudian menggunakan perintah PowerShell ini, Anda dapat memverifikasi integritas file yang diunduh:
PS C:\Distr> (Get-FileHash .\apache-jmeter-4.0.zip -Algorithm MD5).Hash -eq (Get-Content .\apache-jmeter-4.0.zip.md5 | Convert-String -Example "hash path=hash")
Keluaran:
True
Penjelasan:
Operan pertama -eq
operator adalah hasil perhitungan checksum untuk file:
(Get-FileHash .\apache-jmeter-4.0.zip -Algorithm MD5).Hash
Operan kedua adalah nilai checksum yang dipublikasikan. Kami pertama-tama mendapatkan konten file.md5 yang merupakan satu string dan kemudian kami mengekstrak nilai hash berdasarkan format string:
Get-Content .\apache-jmeter-4.0.zip.md5 | Convert-String -Example "hash path=hash"
Baik file dan file.md5 harus berada di folder yang sama untuk pekerjaan perintah ini.
Inilah yang saya gunakan untuk mendapatkan nilai hash yang konsisten:
function New-CrcTable {
[uint32]$c = $null
$crcTable = New-Object 'System.Uint32[]' 256
for ($n = 0; $n -lt 256; $n++) {
$c = [uint32]$n
for ($k = 0; $k -lt 8; $k++) {
if ($c -band 1) {
$c = (0xEDB88320 -bxor ($c -shr 1))
}
else {
$c = ($c -shr 1)
}
}
$crcTable[$n] = $c
}
Write-Output $crcTable
}
function Update-Crc ([uint32]$crc, [byte[]]$buffer, [int]$length, $crcTable) {
[uint32]$c = $crc
for ($n = 0; $n -lt $length; $n++) {
$c = ($crcTable[($c -bxor $buffer[$n]) -band 0xFF]) -bxor ($c -shr 8)
}
Write-Output $c
}
function Get-CRC32 {
<#
.SYNOPSIS
Calculate CRC.
.DESCRIPTION
This function calculates the CRC of the input data using the CRC32 algorithm.
.EXAMPLE
Get-CRC32 $data
.EXAMPLE
$data | Get-CRC32
.NOTES
C to PowerShell conversion based on code in https://www.w3.org/TR/PNG/#D-CRCAppendix
Author: Øyvind Kallstad
Date: 06.02.2017
Version: 1.0
.INPUTS
byte[]
.OUTPUTS
uint32
.LINK
https://communary.net/
.LINK
https://www.w3.org/TR/PNG/#D-CRCAppendix
#>
[CmdletBinding()]
param (
# Array of Bytes to use for CRC calculation
[Parameter(Position = 0, ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[byte[]]$InputObject
)
$dataArray = @()
$crcTable = New-CrcTable
foreach ($item in $InputObject) {
$dataArray += $item
}
$inputLength = $dataArray.Length
Write-Output ((Update-Crc -crc 0xffffffffL -buffer $dataArray -length $inputLength -crcTable $crcTable) -bxor 0xffffffffL)
}
function GetHash() {
[CmdletBinding()]
param(
[Parameter(Position = 0, ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[string]$InputString
)
$bytes = [System.Text.Encoding]::UTF8.GetBytes($InputString)
$hasCode = Get-CRC32 $bytes
$hex = "{0:x}" -f $hasCode
return $hex
}
function Get-FolderHash {
[CmdletBinding()]
param(
[Parameter(Position = 0, ValueFromPipeline = $true)]
[ValidateNotNullOrEmpty()]
[string]$FolderPath
)
$FolderContent = New-Object System.Collections.ArrayList
Get-ChildItem $FolderPath -Recurse | Where-Object {
if ([System.IO.File]::Exists($_)) {
$FolderContent.AddRange([System.IO.File]::ReadAllBytes($_)) | Out-Null
}
}
$hasCode = Get-CRC32 $FolderContent
$hex = "{0:x}" -f $hasCode
return $hex.Substring(0, 8).ToLower()
}
Berikut ini cuplikan yang saya gunakan untuk mendapatkan MD5 untuk string yang diberikan:
$text = "text goes here..."
$md5 = [Security.Cryptography.MD5CryptoServiceProvider]::new()
$utf8 = [Text.UTF8Encoding]::UTF8
$bytes= $md5.ComputeHash($utf8.GetBytes($text))
$hash = [string]::Concat($bytes.foreach{$_.ToString("x2")})