如何在GCP中使用secp256k1算法设置密钥库?

时间:2019-09-22 22:00:47

标签: google-cloud-platform

我必须使用secp256k1算法将密钥库设置为Google Cloud Platform服务,但不知道从哪里开始。

我检查了可用选项,并仅找到椭圆曲线P-256-SHA256摘要支持。这和secp256k1一样吗?

1 个答案:

答案 0 :(得分:1)

如果您的第一句话是要与Google Cloud Platform提供Key Vault类似(至少部分)的服务(即Cloud Key Management Service又称为KMS),那么答案是否定的。 / p>

对于Azure的Key Vault,椭圆曲线SECP256K1 is available目前是Cloud KMS仅有的椭圆曲线available are P-256和P-384。

P-256SECP256K1曲线并不相同,到目前为止,FIPS-186-4和{{3}中的P-256中定义了SECP256K1 }。

无论如何,要支持所有这些,您可以运行以下实验。

使用Cloud SDK(Standards for Efficient Cryptography Version 2)创建ASYMMETRIC_SIGN目的密钥:

keyring=keyring0
key=key0
location=US
gcloud kms keyrings create $keyring --location=$location
gcloud kms keys create $key --location $location --keyring $keyring --purpose asymmetric-signing --default-algorithm ec-sign-p256-sha256 --protection-level software

签名消息并导入先前生成的(即KMS生成的)密钥对的公共密钥。

message=message
signature=message.sig
echo $(date):$(uname -a) > $message
gcloud kms asymmetric-sign --keyring=$keyring --key=$key --location=$location --input-file=$message --signature-file=$signature --digest-algorithm=sha256 --version=1
gcloud kms keys versions get-public-key 1 --location=$location --keyring=$keyring --key=$key --output-file=./$keyring-$key.pub

现在您可以使用openssl dgst -verify $keyring-$key.pub -signature $signature $message来验证签名,但是您将不会获得有关用于生成密钥对的椭圆曲线的信息,而密钥对是使用密钥进行签名的。

要获取该信息,我们可以安装Python第三方库:

virtualenv --python=/usr/bin/python3 ecdsa
cd ecdsa
source bin/activate
pip install ecdsa

并运行以下命令来验证签名,并在选择签名算法ec-sign-p256-sha256时查看KMS使用的曲线:

python3 -c """
from pathlib import Path
import hashlib
from ecdsa import VerifyingKey, BadSignatureError

publickey = Path('$keyring-$key.pub')
signature = Path('$signature')
message = Path('$message')

def read_signature(signature):
    '''
    workaround for https://github.com/warner/python-ecdsa/issues/67
    more background on why's that in https://tools.ietf.org/html/rfc5652
    '''
    LEN = 64
    LENHALF = LEN//2
    with signature.open('rb') as fp:
        sig = fp.read()

    offset = 4 if sig[4] else 5
    slice_s, slice_r =  slice(offset, offset + LENHALF), slice(-LENHALF, len(sig))   
    s,r = sig[slice_s], sig[slice_r]
    return s + r

def verify(publickey, signature, message):

    with publickey.open() as pkfp, message.open('br') as messagefp:
        vk = VerifyingKey.from_pem(pkfp.read())
        try:
            print('Verifying with public key associated with curve', repr(vk.curve.name))
            vk.verify(read_signature(signature), messagefp.read(), hashfunc=hashlib.sha256)
            print('Verify Success')
        except BadSignatureError:
            print('Verify Failure')

verify(publickey, signature, message)
"""

要锤击本示例中用于KMS的椭圆曲线的点原点为NIST的P-256及其与SECP256K1的参数差异,请查看以下代码片段:

python3 -c """
from collections import namedtuple 
from operator import attrgetter
from ecdsa import NIST256p, SECP256k1

sextuple = namedtuple('T', 'p, a, b, G, n, h')

ag_curve = attrgetter(*('curve._CurveFp__'+c for c in 'abp'))
ag_generator = attrgetter(*('generator._Point__'+c for c in 'x y order'.split()))

def make_sextuple(curve, h=1):
    n, G_x, G_y = ag_generator(curve)
    return sextuple(*ag_curve(curve), n=n, G=(G_x, G_y), h=h)

T_NIST256p = make_sextuple(NIST256p)
T_SECP256k1 = make_sextuple(SECP256k1)

if T_NIST256p != T_SECP256k1:
    for k in sextuple._fields:
        ag_k = attrgetter(k)
        v0, v1 = ag_k(T_NIST256p), ag_k(T_SECP256k1)
        if v0 != v1:
            print('Different values for parameter ', k,)
            print(v0)
            print(v1)
"""