go解析含passphrase的pem秘钥

embedded/2024/9/23 7:29:58/

背景

在编写TLS配置时需要用到需要用到一串包含passphrase的RSA秘钥,本想通过官方库的方式解析使用,但由于安全因素,官方已经禁用了DecryptPEMBlockEncryptPEMBlockIsEncryptedPEMBlock等函数,导致无法通过官方库去实现这个需求。

解决方案

最终通过pkcs8库来完成需求,代码如下:

go">package mainimport ("crypto/x509""encoding/pem""fmt""os""github.com/youmark/pkcs8"
)func main() {pem, err := getTlsConfig()if err != nil {panic(err)}fmt.Println("无加密的pem:", string(pem))
}func getTlsConfig() ([]byte, error) {passphrase := "test123"keyFilePaaht := "./key"keyPEMByte, err := os.ReadFile(keyFilePaaht)if err != nil {err = fmt.Errorf("read %s failed! err: %s", keyFilePaaht, err)return nil, err}keyPEMBlock, rest := pem.Decode(keyPEMByte)if len(rest) > 0 {err := fmt.Errorf("decode key failed! rest: %s", rest)return nil, err}// 解析pemkey, err := pkcs8.ParsePKCS8PrivateKey(keyPEMBlock.Bytes, []byte(passphrase))if err != nil {err = fmt.Errorf("parse PKCS8 private key err: %s", err)return nil, err}// 解析出其中的RSA 私钥keyBytes, err := x509.MarshalPKCS8PrivateKey(key)if err != nil {err = fmt.Errorf("MarshalPKCS8PrivateKey failed! %s", err)return nil, err}// 编码成新的PEM 结构newKey := pem.EncodeToMemory(&pem.Block{Type:  "PRIVATE KEY",Bytes: keyBytes,},)return newKey, nil
}

为什么GO不支持pem的加密?

GO团队的Commit Message:

crypto/x509: deprecate legacy PEM encryption
It’s unfortunate that we don’t implement PKCS#8 encryption (#8860)
so we can’t recommend an alternative but PEM encryption is so broken
that it’s worth deprecating outright.

官方库x509:

Deprecated: Legacy PEM encryption as specified in RFC 1423 is insecure by design. Since it does not authenticate the ciphertext, it is vulnerable to padding oracle attacks that can let an attacker recover the plaintext.

GO团队认为PEM encryption的实现是不好的,不够安全的,因此官方移除了实现,并且也不推荐相关的外部实现的库。

从这个Issue的讨论可以看出社区对这个需求的渴望已经很久,但官方并没有太多关注。

参考链接

  • Github Issue - crypto/x509: “certificate is not standards compliant” on MacOS
  • Github Issue - Encrypted private key in PKCS#8 format not supported #17
  • x509-decryptpemblock-is-deprecated-what-is-alternative

http://www.ppmy.cn/embedded/38043.html

相关文章

vue快速入门(五十)重定向

注释很详细,直接上代码 上一篇 本篇建立在之前篇目前提下针对重定向进行演示 新增内容 路由重定向写法 源码 src/router/index.js //导入所需模块 import Vue from "vue"; import VueRouter from "vue-router"; import myMusic from "/v…

三层交换机与防火墙连通上网实验

防火墙是一种网络安全设备,用于监控和控制网络流量。它可以帮助防止未经授权的访问,保护网络免受攻击和恶意软件感染。防火墙可以根据预定义的规则过滤流量,例如允许或阻止特定IP地址或端口的流量。它也可以检测和阻止恶意软件、病毒和其他威…

学习大数据,所需更要的shell基础(2)

文章目录 read读取控制台输入函数系统函数bashnamedirname 自定义函数Shell工具(重点)cutawk 正则表达式入门常规匹配常用特殊字符 read读取控制台输入 1)基本语法 read (选项) (参数) ①选项: -p:指定读取值时的提示…

SARscape操作:GF3 数据预处理

1、设置 Prefrences 参数 点击 SARscape->Preferences->Preferences specific,弹出如下图所示的对话框; 点击 Load Preferences,在弹出的菜单栏中选择适用于GF3影像处理的 MR(between 10m and 30m) 模式; 点击 General p…

DAY 3

1. #include "widget.h"Widget::Widget(QWidget *parent): QWidget(parent) {this->resize(540,415);this->setFixedSize(540,415);//窗口标题this->setWindowTitle("盗版QQ");//窗口图标this->setWindowIcon(QIcon("E:\\qq\\pictrue\\pi…

onedrive下載zip檔案有20G限制,如何解決

一般來說,OneDrive網頁版對文件下載大小的限制如下圖所示,更多資訊,請您參考這篇文章:OneDrive 和 SharePoint 中的限制 - Microsoft Support 因此我們推薦您使用OneDrive同步用戶端來同步到本地電腦,您也可以選擇只同…

C盘下.m2文件名夹,以及文件详解

${user.home}/.m2/repository文件夹 是maven默认的本地仓库地址 maven仓库分为远程仓库和本地仓库,当你在pom里配置依赖项目后,maven首先会从本地仓库查找该项目,如果没有找到则通过配置的地址或默认地址(如果没有配置远程仓库地…

Docker入门篇来啦~

文章目录 1虚拟化技术1.1 硬件级虚拟化1.2 操作系统级虚拟化 2 Docker是什么2.1 Docker介绍2.2 容器和虚拟机的区别2.3 为什么使用Docker 3 Docker运行环境部署3.1 Docker安装3.2 Docker服务启动 4 Docker核心组件4.1 镜像4.1.1 镜像的基本概念4.1.2 镜像的组成结构4.1.3 镜像的…