数据安全--KMS

背景介绍

密钥管理服务(KMS)是一套密钥管理系统, 可以针对云上数据/各端上的加密需求精心设计的密码应用服务,为您的应用提供符合各种要求的密钥服务及极简应用加解密服务,助您轻松使用密钥来加密保护敏感的数据资产。

方案

开发者身份受保护数据保护目的解决方案
网站或应用开发证书、密钥网站和应用会使用HTTPS证书来保证通信协议的安全,也会使用密钥来给文件打上自己企业的签名,但是这些常见的安全解决方案非常依赖证书和密钥本身的安全。KMS密钥管理
后台服务开发密码、登录密钥、配置数据库密码、登录密钥、后台服务的配置信息可能会被黑客利用,明文存储在硬盘上非常危险。KMS密钥管理
内容、社交网站或应用用户原创内容、有价值的知识产权企业依赖核心的UGC内容或独特的知识产权来建立在行业的竞争优势,一定不能发生『拖库』这样的事故。KMS信封加密
政府、金融机构协议通信内容、重要文件和资料政府和金融机构任何的通信和存储数据都具有高价值性和高保密性,需要在建立业务系统时就考虑好合规性和安全性。KMS信封加密

架构

在这里插入图片描述

架构图描述:

  1. KMS: 根密钥生成,为了生成根密钥的保密性,由三个人分别输入三段约定好算法的随机因子到HSM中去生成根密钥,非法读取HSM中的根密钥会导致HSM被破坏而不可用从而保护了根密钥不被泄露。另外为了保存好根密钥以备及时恢复,要将三段随机因子分别保存到三个保险柜中。为了防止根密钥被泄露,根密钥RootKey由密钥管理服务KMS从硬件安全模块即HSM中读取,按照一定的分散算法打散存储在内存中。
  2. SDK: 开发者将SDK集成到自己开发的服务或者系统的代码中,以实现只需要调用较为简单抽象的接口就能够使用密钥管理服务的相关功能。SDK中进行加解密是为了防止业务方私自保存密钥。Client主要是负责SDK的Http请求相关的功能,加解密模块则是负责SDK加解密相关的功能。

KMS核心功能

包括密钥生命周期:
1、密钥生成 - 统一管理密钥的生成,一般要求根密钥具备较高的随机性以防止密钥被猜测、应用密钥通过安全的分散算法派生生成。
2、密钥存储 - 安全的存储密钥,如使用专用的安全存储设施或采用高强度加密保护,防止密钥的泄露和窃取。
3、密钥分发 - 确保密钥从生成、存储环境向使用环境传输的过程中不被泄露。
4、密钥注销 - 密钥生命周期完结之后,合理、安全地销毁密钥,并对销毁步骤作进行记录。
5、密钥更新 - 通过合理的密钥更替机制,降低密钥长期使用带来的暴露风险。一般要求:根密钥长期有效,具备更替能力;应用密钥定期更新,防止恶意破解;过程密钥一次一密,并通过引入时间戳、流水号等应用数据防止重放攻击。
6、密钥备份 - 保证重要密钥的备份恢复机制,在密钥丢失、灾难场景下,能够较快恢复密码服务能力,恢复时间目标(RTO)和恢复点目标(RPO)满足业务方需求。
7、密钥应用和密码运算服务 - 在具体的应用场景下,KMS还负责为业务方提供与应用相关的安全接口,如:数据加密封装、隐私数据脱敏、接口签名等。

一般情况下我们将KMS系统划分为三个核心模块
1、安全区 - 整个系统的安全根,主要负责安全存储系统的根密钥,仅对系统内必要的功能模块开放访问权限。
2、服务层 - 系统主要功能的实现部分,为用户和KMS的应用提供密钥管理、数据加密、数字签名等服务,这也是KMS中与业务逻辑关系最紧密的部分。
3、接入层 - 面向应用系统提供业务接入能力,通过提供多语言、多框架适配的SDK,来支持无侵入或低侵入的集成。

密钥生成

从网上弄了一个图,大致如下:
在这里插入图片描述

  • 初始密钥的密钥因子:用于导出初始秘钥。
  • 初始密钥:用于加密工作密钥。
  • 工作密钥:用于加密敏感数据(密码、个人信息等)的密钥。
生成
  1. 导出初始密钥的初始向量的生成
    使用安全随机数算法生成16字节随机数,并做一些其他随机运算(参见已实现的代码)。并写死在代码中,不再更改。

  2. 导出初始密钥的密钥因子的生成
    使用安全随机数算法生成16字节随机数,并以16进制形式保存在密钥因子文件中。

  3. 初始密钥生成
    PBKDF2算法是一个标准的密钥导出算法,可用于导出对称密钥,计算公式为:

DK  =  PBKDF2(Password, Salt, count, dkLen)
输入:
  Password:用户输入的口令或者读取的一串字符串,这里使用"密钥因子"。
  Salt  :盐值,字符串,这里使用"初始向量"
  count :迭代次数,正整数,默认使用"50,000"次
  dkLen :导出密钥的字节长度,正整数,该长度需根据应用程序或密码应用模块所需要的工作密钥长度来定义,以AES128加密算法为例,密钥长度为128bit,即16字节。
输出:
  DK :导出的密钥,长度为dkLen个字节的字符串。


Hash函数:
优先使用HmacSHA256、HmacSHA384、HmacSHA512等强密码算法,如果是由于使用的加密库等方面的原因导致不支持相应的强密码算法,也可以使用HmacSHA1,但迭代次数(count)需定义为"100000""次。


Java示例代码:
  SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
  1. 工作密钥的生成
    使用安全随机数算法生成16字节随机数,再使用初始秘钥加密,将结果保存在工作秘钥文件中。

密钥更新

在密钥泄露、到期等原因下,需要更新秘钥。

代码参考:
https://github.com/xdc0209/java-code/blob/master/basicKnowledge/src/com/xdc/basic/skills/encrypt/aes/%E4%B8%80%E7%A7%8D%E5%AE%89%E5%85%A8%E5%BA%A6%E8%BE%83%E9%AB%98%E7%9A%84AES%E5%8A%A0%E5%AF%86%E7%AE%97%E6%B3%95%E7%9A%84%E4%BD%BF%E7%94%A8%E6%96%B9%E5%BC%8F.txt

https://kyakya.icu/article/java%E5%AF%86%E7%A0%81%E5%AD%A6-10.%E6%95%B0%E5%AD%97%E4%BF%A1%E5%B0%81#KEK

密钥派生

KMS中最为关键的模块是密钥派生模块。根据用户ID和随机因子通过伪随机函数派生出KEK或者DEK等密钥。KMS杜绝明文持久化保存密钥,派生出来的KEK通过Rootkey加密保存在数据库,派生出来的DEK通过KEK加密保存在数据库。

创建密钥:
1.用户调用KMS提供的SDK创建用户数据密钥
2.用户传入用户ID等必要信息(如果要创建KEK则传入部门信息,如果创建DEK则传入应用信息)
3.KMS服务器验证请求
4.验证通过,KMS服务器在该用户名下创建新的密钥并返回密钥ID

数据加密过程:
1.KMS系统随机生成DEK
2.使用DEK对数据进行加密
3.使用KEK对DEK进行加密
4.将加密后的数据和加密后的DEK一并存入数据库

数据解密过程:
1.从数据库提取出加密后的数据和加密后的DEK
2.使用KEK对加密后的DEK进行解密
3.使用解密后的DEK对加密后的秘闻数据进行解密,得到原始数据

第一层:工作密钥,DEK,用来加密实际的敏感数据。
第二层:密钥加密密钥,又叫做终端主密钥,KEK,用来加密工作密钥,在各个终端中存在。
第三层:非对称密钥,数字证书的一部分,用来识别身份,并加密传输KEK。

KDF (key derivation function,密钥派生函数) 可以通过特定算法将密码派生出指定长度的密钥,非常适用于密码验证的密码哈希处理。
常用于密码哈希的 KDF 算法有 bcrypt,scrypt,Argon2,PBKDF2。在 2013 到 2015 年间进行的密码哈希竞赛宣布 Argon2 成为获胜者,所以目前最为推荐用于密码哈希的算法就是 Argon2。

Go 中提供了 golang.org/x/crypto,其中包括常用的 KDF:
Argon2, golang.org/x/crypto/argon2。
Bcrypt, golang.org/x/crypto/bcrypt。
Scrypt, golang.org/x/crypto/scrypt。
PBKDF2, golang.org/x/crypto/pbkdf2。
HKDF, golang.org/x/crypto/hkdf。

密钥管理

初始化阶段:
1.各个Service首先在KMS中接入获得身份令牌token
2.各个Service生成自己的RSA公私钥
3.各个Service拿自己的RSA公钥去CA申请证书

密钥准备阶段:
1.Service用自己的证书去KMS申请需要的密钥
2.密钥保存在Service本地,定期去KMS重新获取(当有效期设置为0时,即不在Service本地保存,一次一密)

业务调用阶段:
1.Service用获取到的签名密钥做签名,加密密钥做加密,调用其他服务。
2.其他业务线校验签名,返回数据。

密钥轮换

广泛重复的使用加密密钥,会对加密密钥的安全造成风险。为了确保加密密钥的安全性,用户需要为用户主密钥创建新的密钥材料。

用户可以通过以下两种方式创建新的密钥材料:

  • 创建新的用户主密钥。
  • 为现有的用户主密钥开启密钥轮换,KMS自动为用户主密钥生成新的密钥材料。密钥轮换只会更改用户主密钥的密钥材料,用户主密钥的属性(密钥ID、别名、描述、权限)不会发生变化。

开启密钥轮换后,密钥管理服务会根据设置的轮换周期(默认365天)自动轮换密钥,每次轮换都会生成一个新版本的用户主密钥,轮换的密钥加解密数据的方式,如下所示:

  • 加密数据时,KMS会自动使用当前最新版本的用户主密钥来执行加密操作。
  • 解密数据时,KMS会自动使用加密时所使用的用户主密钥来执行解密操作。

密钥管理服务会保留与该用户主密钥关联的所有版本的用户主密钥。这使得KMS可以解密使用该用户主密钥加密的任何密文。

默认主密钥和外部导入的密钥不支持密钥轮换。

开启轮换:
1.可根据设定时间进行轮转(定期更换)
2.开启后直接使用最新的密钥版本

未开启轮换:
根据密钥的版本进行使用

密钥使用

设备和服务可通过请求参数获取自己的密钥套件, 
request: {
    type: 1/2/3
    ak: uuid
    rk: 随机16位数
    device:{
        dsn = value.get('Device Serial Number') +
        password = value.get('Password') +
        dev_id = value.get('Device Identifier')
        net_id = value.get('Network Identifier')
        mach_id = value.get('Machine Identifier')
        med_id = value.get('Media Identifier')    
    }
}
申请后返回:车机的话每个uid一套,减少链接延迟可设置轮换(主要用于传输协议和预埋密钥)
KeySuite: {
deviceId:
keyId:
keySecret: {
    aesKey:    
    aesKeyHash:    
    hmacKey:  
    hmacKeyHash: 确认唯一性编码
} 
}
1.可根据版本进行密钥使用

密钥吊销

服务公私钥泄漏后,需要吊销。吊销过程如下:
将需要吊销的公钥导入到离线的根密钥管理系统中,生成吊销列表,由根私钥对吊销列表签名;
将吊销文件通过OTA升级(车机)、软件升级(手机APP)的形式内置到Android Framework或APP中;
车机、手机验签时先检查服务公钥是否在吊销列表中,如果在吊销列表中,验签失败,如果没在吊销列表中,执行后续的验签动作;

验证签名

可采用层级验证签名的方式进行

应急处理

主密钥和业务密钥可以进行备份(CDC机制)
根密钥直接复制一份保留(存储方式根据自己的公司进行制定)
密钥相关系统运行在安全区

思考

1、什么时候做数字签名?
每次接口调用都做数字签名。

2、数据加密的算法?
建议采用对称加密AES256位密钥,待加密的数据类型不同,选择不同模式,一般情况下CBC模式适合大多数场景,XTS模式适合本地存储场景。

3、如何判断一条数据是否被加密?
在系统迁移的过程中,必然出现明文和加密两种逻辑同事出现的情况,此时就需要程序判断数据是明文还是密文,建议在SDK中提供方法判断。

4、存储加密数据库索引如何处理?
基于安全的设计,相同的明文可能密文不同,因此需要建立一条不可逆并且与明文一一对应的值做索引。

5、存储加密历史数据如何处理?
第一次加密之前的历史数据,需要提前先由刷库工具统一将明文刷成密文,刷库时,需要先新建一列密文列,将明文列加密后刷到密文列中,之后程序写入或者更新操作时,需要对明文列、密文列双写,读取操作时只读取密文列,等程序稳定运行一段时间后,再将明文列删除。第一次加密之后,随着密钥定期更新,不同时期的数据使用不同密钥加密。

6、密钥如何存储?
在KMS服务端,工作密钥需要加密存储于数据库中,加密存储的密钥可采用分段式密钥,通过RAID方式将不同密钥段存储于不同介质中。

7、证书如何生成下发?
证书生成下发通常有两种方式,第一种是SDK生成RSA公私钥,将RSA公钥发给CA申请证书,CA用自己的私钥签发证书后返回给SDK。第二种是直接CA生成RSA公私钥,并签发证书,并下发给SDK。这两种方式可根据实际业务需求选择。证书是对客户端做身份识别的最重要标识,因此在第一次下发证书时,建议采用可信的第三方系统独立下发,如SRE发布系统。如果有有效且安全的手段保证客户端的合法性,可通过SDK与KMS的交互来下发证书。

8、证书如何验证,保证客户端的合法性?
证书验证需要两个步骤:
(1)验证证书的合法性,通过CA的公钥解密证书,校验签名即可验证证书的合法性、未被篡改。(2)验证客户端持有证书对应的私钥,KMS向SDK发起challenge,向SDK发送一个随机数,SDK使用私钥加密后,返回给KMS,KMS使用证书中的公钥解密,验证SDK确实持有合法的私钥,证明SDK的合法身份。为了保证安全性,KMS发送的随机数可以做一次哈希。

9、密钥协商方式?
密钥协商可采用集中协商或者分散协商两种方式。
(1)集中协商:各个SDK分别向KMS请求密钥,KMS生成后返回给各个SDK。
(2)分散协商:假设有两个客户端A和B,A和B使用DH密钥协商算法,来协商密钥。

10、容器怎么调用密钥?
容器直接以sidecar方式运行

11、怎么保证service端运行的密钥安全?
难点:agent运行安全和本身安全保证

12、身份认证方式?
a. 采用ak/sk认证—ram访问管理控制
b. 采用IAM(outh2协议)认证/IDaas

参考

密钥管理架构设计概述
https://segmentfault.com/a/1190000019179595
分布式密钥管理系统(Tenzorum/NuCypher)
https://mp.weixin.qq.com/s/u6EFAn4lqYFZYvZsCGhrRw
密钥交换算法
https://www.liaoxuefeng.com/wiki/1252599548343744/1304227905273889
go密钥依赖库(SM2/SM3/SM4[分组密码算法]/x509)
https://github.com/tjfoc/gmsm
https://studygolang.com/articles/21300
密钥分散算法/打散算法的三种解决方案及选型场景
https://zhuanlan.zhihu.com/p/191017039
AK/SK身份认证系统
https://blog.51cto.com/u_15301988/3127042#Step_1_AKSK_29
https://zhuanlan.zhihu.com/p/109988929 (hmac)
https://www.cnblogs.com/wangzhen-fly/p/11091254.html (您可以为ak生成UUID,为sk生成随机字节)
https://github.com/huaweicloudDocs/iam/blob/master/cn.zh-cn/API%E5%8F%82%E8%80%83/%E8%AE%A4%E8%AF%81%E9%89%B4%E6%9D%83.md
谈AK管理之基础篇 - 如何进行访问密钥的全生命周期管理?
https://developer.aliyun.com/article/782639
https://developer.aliyun.com/article/782641?utm_content=g_1000254832
爱奇艺kms
https://www.secrss.com/articles/34234
开源的几个kms相关
https://www.cnblogs.com/2018/p/14356796.html
TLS 中的密钥计算
https://halfrost.com/https-key-cipher/#toc-3
kmip使用
https://pkg.go.dev/github.com/gemalto/kmip-go#example-Server
https://blog.csdn.net/lihuayong/article/details/19121655?utm_source=app&app_version=4.21.0&code=app_1562916241&uLinkId=usr1mkqgl919blen
https://blog.csdn.net/lihuayong/article/details/25098093?spm=1001.2101.3001.6650.8&utm_medium=distribute.pc_relevant.none-task-blog-2%7Edefault%7EBlogCommendFromBaidu%7Edefault-8.no_search_link&depth_1-utm_source=distribute.pc_relevant.none-task-blog-2%7Edefault%7EBlogCommendFromBaidu%7Edefault-8.no_search_link&utm_relevant_index=9
https://github.com/smira/go-kmip/blob/a8ea65df664e89a2edd6f7558988c753960d2145/client.go
https://pykmip.readthedocs.io/en/latest/server.html#configuration
加密信封和生成证书
https://kyakya.icu/article/java%E5%AF%86%E7%A0%81%E5%AD%A6-11.%E7%94%9F%E6%88%90%E8%87%AA%E8%AF%81%E4%B9%A6%E5%92%8C%E7%AD%BE%E5%90%8D%E8%AF%81%E4%B9%A6
python创建证书
https://github.com/OpenKMIP/PyKMIP/blob/645cbf2ae931b03b8f5ebe2458683da1b2276794/bin/create_certificates.py
ssl/tls
https://blog.csdn.net/vip97yigang/article/details/84721027
https://zhuanlan.zhihu.com/p/438843363
https://github.com/cloudflare/cfssl
go grpc
https://segmentfault.com/a/1190000019216566
KMIP文档(要求使用TLS相互身份认证,本身有一套密钥操作模板)
https://www.ibm.com/support/pages/sites/default/files/inline-files/$FILE/chs_kmip.pdf

vault
https://huangjunwen.github.io/post/2017/vault/
https://huangjunwen.github.io/post/2017/shamir-secret-sharding/
vault安装
https://www.secrss.com/articles/11755
https://shuhari.dev/blog/2018/02/vault-introduction
docker vault
https://shuhari.dev/blog/2018/02/vault-introduction
https://jenkins-zh.blog.csdn.net/article/details/105548898?spm=1001.2101.3001.6650.3&utm_medium=distribute.pc_relevant.none-task-blog-2%7Edefault%7ECTRLIST%7Edefault-3.no_search_link&depth_1-utm_source=distribute.pc_relevant.none-task-blog-2%7Edefault%7ECTRLIST%7Edefault-3.no_search_link&utm_relevant_index=6
kmip in vault
https://learn.hashicorp.com/tutorials/vault/kmip-engine
vault策略管理
https://learn.hashicorp.com/tutorials/vault/policies?_x_tr_sl=auto&_x_tr_tl=zh-CN&_x_tr_hl=zh-CN&_x_tr_pto=op

vsm产品
http://www.westone.com.cn/products/40/135.html
云密码服务技术白皮书
http://www.bccia.org.cn/upload/files/2019/12/19f490f47a6d26bd.pdf

  • 8
    点赞
  • 35
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值