一. 什么是单向散列函数
单向散列函数有多个术语变体,又称为消息摘要函数,或者哈希函数,或者杂凑函数。它主要应用在为一个输入消息输出一个对应的散列值(又称哈希值),不同的输入消息输出的散列值一般是不相同的(相同碰撞概率很小),因此可以用来检验消息的完整性。
如下在该网址下载文件时,网址就附上了每个文件对应的 sha256 哈希散列值,当我们下载完对应的文件时,在本地使用 sha256 为下载好的文件生成散列值,就可以校验在传输过程中内容是否被篡改,或者是否下载了正确的文件(不是代理欺骗后的内容)。
使用 openssl 可以生成文件对应的 sha256 散列值。
二. 散列函数的性质
1. 输入任意长度的消息可以得到固定长度的散列值,且计算具有单向性,根据散列值无法推算出原输入消息的性质
2. 计算散列值的时间很短
3. 输入消息不同,输出散列值也不同(有极小的概率也可能相同),对于两个不同的消息产生同一个散列值的情况称为碰撞
三. 散列函数的种类
散列函数类型有 sha-1,sha-224,sha-256,sha-384,sha-512,md4,md5 等。
md4 和 md5 都可以产生 128bit 的散列值,但是目前已有 md4 散列碰撞的方法,而 md5 也无法防止碰撞攻击,因此它们安全性不高,对于需要高度安全的信息,建议使用 sha-2。
sha-1 可以产生 160bit 的散列值,碰撞性已被攻破,安全性不高。sha-224,sha-256,sha-384,sha-512 统称为 sha-2,它们分别可以产生 224bit,256bit, 384bit, 512bit 的散列值,安全性较高。
类型 | 输出散列值长度 | 安全性 |
MD4 | 128bit | 较低 |
MD5 | 128bit | 较低 |
SHA-1 | 160bit | 较低 |
SHA-224 | 224bit | 较高 |
SHA-256 | 256bit | 较高 |
SHA-384 | 384bit | 较高 |
SHA-512 | 512bit | 较高 |
四. golang实战
package main
import (
"crypto/md5"
"crypto/sha1"
"crypto/sha256"
"crypto/sha512"
"fmt"
)
func test_md5() {
data := []byte("Hello world md5")
fmt.Printf("md5: %x\n", md5.Sum(data))
}
func test_sha1() {
data := []byte("Hello world sha1")
fmt.Printf("sha1: %x\n", sha1.Sum(data))
}
func test_sha2() {
data := []byte("Hello world sha2")
fmt.Printf("sha224: %x\n", sha256.Sum224(data))
fmt.Printf("sha256: %x\n", sha256.Sum256(data))
fmt.Printf("sha384: %x\n", sha512.Sum384(data))
fmt.Printf("sha512: %x\n", sha512.Sum512(data))
}
func test_hash() {
data := []byte("Hello world sha2")
h := sha256.New()
h.Write(data)
res := h.Sum(nil)
fmt.Printf("sha256: %x\n", res)
}
func main() {
test_md5()
test_sha1()
test_sha2()
test_hash()
}