I'm signing my messages using my code below:
def sign_msg_hash(self, msg_hash: HexBytes):
signature = self._kms_client.sign(
KeyId=self._key_id,
Message=msg_hash,
MessageType="DIGEST",
SigningAlgorithm="ECDSA_SHA_256",
)
act_signature = signature["Signature"]
return (act_signature)
However, when trying to do the following:
sign = kms.sign_msg_hash(transaction)
vks = ecdsa.VerifyingKey.from_public_key_recovery_with_digest(
sign, transaction, curve=ecdsa.SECP256k1, hashfunc=sha256
)
I get the following error:
ecdsa.util.MalformedSignature: Invalid length of signature, expected 64 bytes long, provided string is 72 bytes long
Now, when trying to use sign[:64]
instead, it sometimes works but at other times gives me the following error:
raise SquareRootError("%d has no square root modulo %d" % (a, p)) ecdsa.numbertheory.SquareRootError: 6631794589973073742270549970789085262483305971731159368608959895351281521222 has no square root modulo 115792089237316195423570985008687907853269984665640564039457584007908834671663
Im not sure if this has anything to do with the encoding of the signature from the KMS or not, hence I appreciate any help provided.
So after some digging, it turned it out it was a matter of encodings, as the kms sign function returns the signature in DER format
hence to what i did was the following:
I took the signature and split it, and got the r and s values as follows(thats for python):
decoding=ecdsa.util.sigdecode_der(sign,int("fffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141",16))
then concatinated the result (note that r and s should be in big endian order):
new_sign = decoding[0].to_bytes(32, byteorder= 'big') + decoding 1 .to_bytes(32, byteorder= 'big')
then used the new sign:
vks = ecdsa.VerifyingKey.from_public_key_recovery_with_digest( new_sign, transaction, curve=ecdsa.SECP256k1, hashfunc=sha256 )
another thing i encountered was with kms_client.get_public_key() so ill add it here anyways:
First call the method:
kms_pub_key_bytes = kms_client.get_public_key(KeyId=key_id)["PublicKey"]
then get the last 128 chars which are essentially the r and s values
kms_pre_sha3 = kms_pub_key_bytes.hex()[-128:]
from there on do whatever you want with the public key:)
I hope that helps someone, since i for sure needed it.
i will also link an article i read that could further help: https://medium.com/asecuritysite-when-bob-met-alice/der-asn-1-and-crypto-formatting-43c33d8fe639
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.