1
method1:
$echo -n "The quick brown fox jumps over the lazy dog" | openssl sha1 | base64
MmZkNGUxYzY3YTJkMjhmY2VkODQ5ZWUxYmI3NmU3MzkxYjkzZWIxMgo=

method2:
$ echo -n "The quick brown fox jumps over the lazy dog" | openssl sha1 | xxd -r -p | base64
L9ThxnotKPzthJ7hu3bnORuT6xI=

method3:
echo -n "The quick brown fox jumps over the lazy dog" | openssl sha1 | xxd -b -p | base64
MzI2NjY0MzQ2NTMxNjMzNjM3NjEzMjY0MzIzODY2NjM2NTY0MzgzNDM5NjU2NTMxNjI2MjM3MzY2NTM3CjMzMzkzMTYyMzkzMzY1NjIzMTMyMGEK

我基本上是在尝试The quick brown fox jumps over the lazy dog通过 sha1 对输入字符串进行校验和作为校验和,然后对结果进行 base64,我有上面两种方法,我认为这method2是正确的答案,但我必须通过额外的步骤将十六进制转换回xxd -r二进制在我再次将其输入 base64 之前的纯格式-p,为什么我必须做这个额外的步骤?

我在任何地方都找不到 base64 cmd 工具期望输入是二进制的?但是让我们假设,当我将其显式转换为二进制并通过 将其提供给 base64 时mehod3 xxd -b option,结果再次不同。

如果使用编程语言 bcos 可能会更容易,因为我们可以完全控制但通过一些 cmd 工具有点混乱,有人可以帮我解释一下吗?

4

1 回答 1

0

这里有三个不同的结果,因为您将三个不同的字符串传递给base64.

根据您关于base64期望输入为二进制的问题,@chepner 就在这里:

所有数据都是二进制的;text 只是表示文本编码(ASCII、UTF-8 等)的字节流。

中间步骤

为了清楚起见,让我们将共享命令存储在变量中。

$ msg='The quick brown fox jumps over the lazy dog'
$ sha_val="$(printf "$msg" | openssl sha1 | awk '{ print $2 }')"
$ printf "$sha_val"
2fd4e1c67a2d28fced849ee1bb76e7391b93eb12

有几点需要注意:

  • 使用 printf 是因为它更加一致,尤其是当我们比较字节和散列时。
  • awk '{ print $2 }'作为 openssl的管道可能会(stdin)=.

比较字节

我们可以使用 xxd 来比较每个字节的字节数,-c 1000使用 1000 字符的行(即不要为 < 1000 字符的字符串添加换行符)。这对于像 method2 中的输出这样的字符串很有用,其中存在无法打印的控制字符。

方法一

这是 sha 值的十六进制表示。例如,2sha 输出中的第一个32在此结果中,因为 hex 32 <=> dec 50 <=> ASCII/UTF-8 "2"。如果这令人困惑,请查看ASCII 表

$ printf "$sha_val" | xxd -p -c 1000
32666434653163363761326432386663656438343965653162623736653733393162393365623132

方法二

这个输出与 $sha_val 完全相同,因为我们正在从十六进制转换为 ASCII 二进制,然后用 xxd 返回。请注意,base64 不需要将 sha 值从十六进制转换为二进制。

$ printf "$sha_val" | xxd -r -p | xxd -p -c 1000
2fd4e1c67a2d28fced849ee1bb76e7391b93eb12

方法三

xxd 的-p选项覆盖了该-b选项,所以xxd -b -p<=> xxd -p

$ printf "$sha_val$" | xxd -p -c 1000 | xxd -p -c 1000
33323636363433343635333136333336333736313332363433323338363636333635363433383334333936353635333136323632333733363635333733333339333136323339333336353632333133323061

如您所见,base64 生成三个不同的字符串,因为它接收三个不同的字符串。

于 2020-04-14T18:46:24.130 回答