为 SSH 生成私钥+公钥对:ssh-keygen 和 openssl 之间的区别?

为 SSH 生成私钥+公钥对:ssh-keygen 和 openssl 之间的区别?

我想要创建用于 SSH 身份验证的私钥和公钥对。

我不明白这之间的区别:

openssl genrsa -out MyPrivateKey 4096
openssl rsa -in MyPrivateKey -pubout -out MyPublicKey

首先创建一个 RSA 私钥,然后从中派生出公钥,或者:

ssh-keygen -b 4096 -t rsa -f MyFancyKey

在文件“MyFancyKey”中创建一个私钥 RSA 密钥,并在“MyFancyKey.pub”中创建一个相应的公钥。

私钥的结构看起来有些相似,尽管创建的私钥以以下内容openssl开头:
-----BEGIN RSA PRIVATE KEY-----

其中之一ssh-keygen开头是:
-----BEGIN OPENSSH PRIVATE KEY-----

这两种钥匙有本质上的区别吗?


然后是相应的公钥,其中openssl包含:

-----BEGIN PUBLIC KEY-----
  ...base64 encoded...
-----BEGIN PUBLIC KEY-----

而来自的那个ssh-keygen只包含一行:
ssh-rsa XXXXXX...base64 encoded...XXXXX [email protected]

这些本质上是同一种数据,只是格式不同吗?还是它们真的不兼容?

我正在尝试完全理解这一切与 SSH 的关系。例如,为什么我的用户名、我的计算机名称和我的本地网络名称在该密钥中,它不是通常用来访问 SSH 的吗?其他电脑?那台电脑上的用户名是我的,不是我自己的。

答案1

私钥

这两种钥匙有本质上的区别吗?

不,它们本质上是相同的数据。

  • BEGIN RSA PRIVATE KEY表示“PKCS#1”或“PEM”密钥格式,这是 ASN.1 DER 序列化结构的 Base64 编码。它是包含 RSA 参数的基本 ASN.1 序列(nd, ETC)。

    这种格式源自 PEM 电子邮件安全工作,后来成为 S/MIME(因此使用 ASN.1 DER)并且通常用于 SSL/TLS 以及其他通用 RSA。

    长期以来,它也是 OpenSSH 的主要密钥格式(因为 OpenSSH 已经使用了 OpenSSL 的加密代码,因此“加载密钥”和“写入密钥”功能也很方便)。这意味着您可以使用它ssh-keygen -m PEM来生成或转换此类密钥。

  • BEGIN PRIVATE KEY表示“PKCS#8”密钥格式(未加密);其内容与 PEM 格式非常相似,相同的 RSA 参数嵌套在另一个结构中,表明它确实是一个 RSA 密钥。

    PKCS#8 是 PEM 格式的更现代替代品。与 PEM 相比,PKCS#8 格式更清晰地将“有效负载”(密钥算法、加密)与外部 Base64 包装器分开 - 所有元数据现在都在结构内,因此更容易更新新密钥类型。新格式还支持更好的加密密钥密码和 KDF。

    OpenSSH 也将识别这种格式(因为它使用 OpenSSL 进行密钥加载),并且我认为最近的版本也能够创建它。

  • BEGIN OPENSSH PRIVATE KEY是 OpenSSH 为 OpenSSH 发明的一种格式,与 PEM/PKCS 格式不同,它使用 SSHv2 数据包序列化作为其数据结构(不再使用 DER 或 ASN.1)。

    OpenSSH 现在使用这种格式的原因之一是它可以完全避免依赖 OpenSSL,和/或它可以添加新的密钥算法而不必等待 OpenSSL 实现这些密钥的加载/保存 - 这也意味着等待 PKIX 标准化每个新算法的 ASN.1 OID 和结构(这与 SSH 完全无关)。

    例如,OpenSSL 花了一段时间才获得对 Ed25519 的全面支持,在此期间,OpenSSH 既不能使用 OpenSSL 的 libcrypto 进行实际数学运算,也不能加载/保存 Ed25519 密钥文件——这促使创建这种格式。

    OpenSSH 格式的另一个优点是密码加密的密钥使用 bcrypt 进行加密密钥派生;当时 PEM 格式仅限于非常弱的(即易于暴力破解)KDF,甚至 PKCS#8 也只支持稍差的 PKBDF2。

  • PuTTY 有自己的.ppk格式,主要是基于文本的。

    其声称的优势在于它不需要单独的 .pub 文件,因为它只选择性地加密私有参数 - 而早期的 PKCS 格式和后来的 OpenSSH 格式要么加密所有内容,要么不加密任何内容,因此它们需要 .pub 文件,以便它们可以在要求您输入密码来解锁之前提供密钥。

    您可以使用/usr/bin/puttygen在所有这些格式之间进行转换。

  • Java 软件可能使用 PKCS#12 (PFX) 格式,因为它是原生的“Java 密钥库”格式,有些软件甚至可能使用 SSH.COM 所谓的标准格式。

也可以看看:OpenSSH 公钥文件格式?

公钥

这些本质上是同一类型的数据,只是格式不同吗?

是的,它们本质上是相同的数据。

  • BEGIN PUBLIC KEY我认为也是 PKCS#8 – 因此 Base64 内部有一个 DER 序列化的 ASN.1 结构,该结构将其标识为 RSA 密钥,后跟密钥参数(n)。

  • 单行格式部分特定于 OpenSSH,尽管中央 Base64 编码数据的格式与 SSHv2 协议本身(“在线”)中使用的格式完全相同。正如您可能猜到的那样,编码数据使用 SSHv2 数据包序列化 - 但它仍然保留相同的 RSAn值。

也可以看看:OpenSSH 公钥文件格式?

例如,为什么我的用户名、我的计算机名称和我的本地网络名称在该键中

这是一条评论当您有一个长文件时,它可以帮助您区分该公钥与其他公钥authorized_keys

相关内容