12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152 |
- # -*- coding: utf-8 -*-
- import warnings
- import os
- from collections import namedtuple
- from . import djbec
- __all__ = ['crypto_sign', 'crypto_sign_open', 'crypto_sign_keypair', 'Keypair',
- 'PUBLICKEYBYTES', 'SECRETKEYBYTES', 'SIGNATUREBYTES']
- PUBLICKEYBYTES=32
- SECRETKEYBYTES=64
- SIGNATUREBYTES=64
- Keypair = namedtuple('Keypair', ('vk', 'sk')) # verifying key, secret key
- def crypto_sign_keypair(seed=None):
- """Return (verifying, secret) key from a given seed, or os.urandom(32)"""
- if seed is None:
- seed = os.urandom(PUBLICKEYBYTES)
- else:
- warnings.warn("ed25519ll should choose random seed.",
- RuntimeWarning)
- if len(seed) != 32:
- raise ValueError("seed must be 32 random bytes or None.")
- skbytes = seed
- vkbytes = djbec.publickey(skbytes)
- return Keypair(vkbytes, skbytes+vkbytes)
- def crypto_sign(msg, sk):
- """Return signature+message given message and secret key.
- The signature is the first SIGNATUREBYTES bytes of the return value.
- A copy of msg is in the remainder."""
- if len(sk) != SECRETKEYBYTES:
- raise ValueError("Bad signing key length %d" % len(sk))
- vkbytes = sk[PUBLICKEYBYTES:]
- skbytes = sk[:PUBLICKEYBYTES]
- sig = djbec.signature(msg, skbytes, vkbytes)
- return sig + msg
- def crypto_sign_open(signed, vk):
- """Return message given signature+message and the verifying key."""
- if len(vk) != PUBLICKEYBYTES:
- raise ValueError("Bad verifying key length %d" % len(vk))
- rc = djbec.checkvalid(signed[:SIGNATUREBYTES], signed[SIGNATUREBYTES:], vk)
- if not rc:
- raise ValueError("rc != True", rc)
- return signed[SIGNATUREBYTES:]
|