与TPM交互:密钥操作

imToken 是一款全球领先的区块链数字资产管理工具[ZB],帮助你安全管理BTC, ETH, ATOM, EOS, TRX, CKB, BCH, LTC, DOT, KSM, FIL, XTZ 资产,同时支持去中心化币币兑换功能 ...

创建主密钥

TPM主密钥创建方法

TPM中密钥以树型方式存放,父密钥保护子密钥,子密钥保持孙密钥,形成一个树形层级结构。TPM 1.2只有一个树,而TPM 2.0有四个树,这样可以更好地区分不同的应用场景。

TPM密钥树型结构

其中Owner、和层级是固定的,根Key是通过对应的种子生成的,通过种子和一致性的算法,生成的Key是相同的。操作这三个树都需要认证。另一个特殊的Null层级,每次TPM重启时它的种子都会变化imtoken私钥和密码,而种子变化将导致通过该种子产生的Key作废,因此只有临时使用才会用到这个层级,最典型的就是把TPM当作密码协处理器使用。

TPM密钥继承树管理

下面的命令在继承树中创建一个主对象(RSA+):

[root@localhost ~]# tpm2_createprimary -H e -K objectpass -g 0x000b -G 0x0001 -C po.ctx -P endorsepass
ObjectAttribute: 0x00030072
CreatePrimary Succeed ! Handle: 0x800000ff

-C po.ctx将对象上下文保存到po.ctx文件,-K 指定这个主对象的密码是,-P指定的密码为,也就是中设置的根密码。-g指定哈希算法,tpm2-tools 3.1目前支持的算法有:

0x4 or sha1 for TPM_ALG_SHA1 (default)
0xB or sha256 for TPM_ALG_SHA256
0xC or sha384 for TPM_ALG_SHA384
0xD or sha512 for TPM_ALG_SHA512
0x12 or sm3_256 for TPM_ALG_SM3_256

-G指定它的公钥算法,tpm2-tools目前支持的算法有:

0x1 or rsa for TPM_ALG_RSA (default).
0x8 or keyedhash for TPM_ALG_KEYEDHASH.
0x23 or ecc for TPM_ALG_ECC.
0x25 or symcipher for TPM_ALG_SYMCIPHER.

在父Key下创建一个子Key

在刚才创建的 Key下创建一个RSA Key:

[root@localhost ~]# tpm2_create -c po.ctx -K subobjectpass -g 0x000b -G 0x0001 -u key.pub -r key.priv -P objectpass
algorithm:
  value: sha256
  raw: 0xb
attributes:
  value: fixedtpm|fixedparent|sensitivedataorigin|userwithauth|decrypt|sign
  raw: 0x60072
type:
  value: rsa
  raw: 0x1
  rsa: eac93b782a7a8d771b23f81f66f8bb4d1555bfe8f51d1ed8240fe942e82fa6fd30993080bb7b730bc6dc0b04c9ddc2d01eb71dce67e35ee295df17d9edcead1d9b86fb514df9572e3a0723960ed99b4833a50a3324dcc686f11607ad2e510d92b70fa2ec780cf8a9229347563e993665b62e89050b2ce9a1a0234a0e0709f0f6346d8c40c7222a7914cb6620c45ed53711273843f050c99a0617589a3f5872ec6cddccf44064a38dc51003f0e62a479bc9d25196b3391c47d7bd808ca8f729a8b2ae3e202a94f97e814826dc2df04d5d24220d0248cfbf98090133fe260c1b3c3657512ead3da8fbf7fba927cfb6c8982912295594022dcd760ac72f6f181fbf
[root@localhost ~]#

-c 指定父对象的上下文,和前面一样,-g和-G指定加密算法,-u输出公钥,-r输出私钥。

-P指定父对象imToken钱包,也即主对象的密码,。

-K指定这个子对象的密码为。

可以看到密钥有一些属性:

fixedtpm|fixedparent|sensitivedataorigin|userwithauth|decrypt|sign

是指密钥不可移动,只能存在于该TPM中。则是密钥的父亲不可更改,这也表明该密钥是固定在一个TPM的继承树的固定位置的。和sign表示该密钥可以用于解密和签名。

加载密钥

创建的对象并不在TPM中,如果要使用它,需要先加载到TPM。这是因为TPM的空间有限,为了满足多个应用的使用需求,除了少量数据存放在TPM内,经常会存在换入换出的操作,协调多个应用使用有限的TPM资源也是和RM在处理的事情。

[root@localhost ~]# tpm2_load -c po.ctx -u key.pub -r key.priv -n key.name -C obj.ctx -P objectpass
Load succ.
LoadedHandle: 0x80000100
[root@localhost ~]#

-c指定父对象( Key)的上下文,也可以通过-H指定父对象的句柄,择一即可。对象在TPM内才有对应的句柄。我们可以将句柄持久化,否则被换出后,需要重新加载才可以使用。

-P指定父对象的密码,-u和-r指定之前创建子对象时输出的密钥和公钥。

-C将这个子对象的上下文保存到obj.ctx,-n可以把该对象的名称输出,这个也是不可读的。

[root@localhost ~]# cat key.name
PZ�f�-�>�G��&��w�hr��~�� �U�#3Su[root@localhost ~]#

使用密钥做RSA加解密

和提供RSA加解密操作。

先来看加密:

[root@localhost ~]# cat sample.txt
hello world!
[root@localhost ~]# tpm2_rsaencrypt -c obj.ctx -o sample.encrypted sample.txt
[root@localhost ~]# cat sample.encrypted
#rit/�wA���
           B#���#Fު#	e#�Z&|�䌕��#KL�#�:##���/Gt
                                                  "�8/�}8�@h'�
�#�<�mڋL���e�ѭ��#ɻ�x
]\���8h�ei���
             �#�)7�e������K���#����8�?��q#HU�P�����:��a�l�8b��F�n�#�(���D��R	ϡ:#�#�d�E&�f��#�#k�'�ʺ��|��^]�e��'�����>������##������Ν#��#�N*B&��#��J#���"�ۡ�B��[root@localhost ~]#

这里使用的是子对象的上下文obj.ctx进行操作的,没有使用密码,应该是采用的公钥加密。如果Key在TPM内,也可以用-k指定句柄来操作。

再把密文解出来:

[root@localhost ~]# tpm2_rsadecrypt -c obj.ctx -o sample.decrypted -I sample.encrypted -P subobjectpass
[root@localhost ~]# cat sample.decrypted
hello world!
[root@localhost ~]#

这里是用私钥解密,所以需要提供密码。

签名和签名校验

继续上面的例子,使用进行签名:

[root@localhost ~]# cat message.txt
this is a message from me.
[root@localhost ~]# tpm2_sign -c obj.ctx -P subobjectpass -g 0x000b -m message.txt -s sig.out

签名文件输出到sig.out

可以用对签名进行校验:

[root@localhost ~]# tpm2_verifysignature -c obj.ctx -g 0x000b -m message.txt -s sig.out -t tk.sig
b4 c7 56 18 8c c9 32 6a 35 1f 41 02 5c 4c c8 78 1a 78 1e 3c fc f0 d8 86 86 fa e6 5e 57 2c e5 0a

修改数据,校验会失败:

[root@localhost ~]# cat modified_message.txt
this is not a message from me.
[root@localhost ~]# tpm2_verifysignature -c obj.ctx -g 0x000b -m modified_message.txt -s sig.out -t tk2.sig
1f 7a 7d c2 32 9e 1e 02 38 fa c4 ae 91 17 2e 00 9e e4 0e ae 10 c3 a7 2a 0c 19 3e 77 90 3d dd 71
ERROR: Tss2_Sys_VerifySignature failed, error code: 0x2db
ERROR: Verify signature failed!
[root@localhost ~]#

对称加密

前面创建的密钥是非对称密钥,要使用对称加密算法,首先要有一个对称加密密钥,方法与非对称加密相同,也需要先通过创建密钥,加载到TPM并隶属于一个父对象,然后使用密钥进行加解密。

现有一段明文:

[root@localhost ~]# cat secrets.txt
this is something I know you know but no others know.

这次在树下创建一个主对象:

[root@localhost ~]# tpm2_createprimary -H e -g sha1 -G rsa -C endorse_primary.ctx
ObjectAttribute: 0x00030072
CreatePrimary Succeed ! Handle: 0x800000ff

创建一个对称加密密钥:

[root@localhost ~]# tpm2_create -g sha256 -G symcipher -u symkey.pub -r symkey.priv -c endorse_primary.ctx
algorithm:
  value: sha256
  raw: 0xb
attributes:
  value: fixedtpm|fixedparent|sensitivedataorigin|userwithauth|decrypt|sign
  raw: 0x60072
type:
  value: symcipher
  raw: 0x25
  symcipher: 7c5168bd5e4e34e7d4a60af97917b6a58e17c11bc76c0b52f06f988def04d942

加载密钥到TPM:

[root@localhost ~]# tpm2_load -c endorse_primary.ctx -u symkey.pub -r symkey.priv -C decrypt.ctx
Load succ.
LoadedHandle: 0x80000100

对明文进行加密:

[root@localhost ~]# tpm2_encryptdecrypt -c decrypt.ctx -I secrets.txt -o secrets.encrypted
[root@localhost ~]# cat secrets.encrypted
����["q�
#x�+T�ӏ�Tdd��������!��)��<#
                           ���|m%���=t�4#�<[root@localhost ~]#
[root@localhost ~]#

对密文进行解密:

[root@localhost ~]# tpm2_encryptdecrypt -c decrypt.ctx -D -I secrets.encrypted -o secrets.decrypted
[root@localhost ~]# cat secrets.decrypted
this is something I know you know but no others know.
[root@localhost ~]#

对称加密算法没有公钥部分,上面命令中所谓的部分是哈希算法和摘要等公开信息。

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

返回顶部
跳到底部

Copyright © 2002-2024 imToken钱包下载官网 Rights Reserved.
备案号:晋ICP备13003952号

谷歌地图 | 百度地图
Powered by Z-BlogPHP Theme By open开发