32 #include "trunnel/ed25519_cert.h"
34 #include "trunnel/link_handshake.h"
46 uint8_t signed_key_type,
47 const uint8_t signed_key_info[32],
48 time_t now, time_t lifetime,
53 ed25519_cert_t *cert = ed25519_cert_new();
55 cert->cert_type = cert_type;
56 cert->exp_field = (uint32_t) CEIL_DIV(now + lifetime, 3600);
57 cert->cert_key_type = signed_key_type;
58 memcpy(cert->certified_key, signed_key_info, 32);
60 if (flags & CERT_FLAG_INCLUDE_SIGNING_KEY) {
61 ed25519_cert_extension_t *ext = ed25519_cert_extension_new();
62 ext->ext_type = CERTEXT_SIGNED_WITH_KEY;
63 memcpy(ext->un_signing_key, signing_key->pubkey.pubkey, 32);
64 ed25519_cert_add_ext(cert, ext);
68 const ssize_t alloc_len = ed25519_cert_encoded_len(cert);
70 uint8_t *encoded = tor_malloc(alloc_len);
71 const ssize_t real_len = ed25519_cert_encode(encoded, alloc_len, cert);
83 log_warn(
LD_BUG,
"Can't sign certificate");
92 log_warn(
LD_BUG,
"Generated a certificate we cannot parse");
99 log_warn(
LD_BUG,
"Generated a certificate whose signature we can't "
111 tor_cert_free(torcert);
116 ed25519_cert_free(cert);
134 time_t now, time_t lifetime,
138 SIGNED_KEY_TYPE_ED25519, signed_key->pubkey,
139 now, lifetime, flags);
162 ed25519_cert_t *parsed = NULL;
163 ssize_t got_len = ed25519_cert_parse(&parsed, encoded, len);
164 if (got_len < 0 || (
size_t) got_len != len)
168 cert->
encoded = tor_memdup(encoded, len);
171 memcpy(cert->
signed_key.pubkey, parsed->certified_key, 32);
172 int64_t valid_until_64 = ((int64_t)parsed->exp_field) * 3600;
173 #if SIZEOF_TIME_T < 8
174 if (valid_until_64 > TIME_MAX)
175 valid_until_64 = TIME_MAX - 1;
180 for (
unsigned i = 0; i < ed25519_cert_getlen_ext(parsed); ++i) {
181 ed25519_cert_extension_t *ext = ed25519_cert_get_ext(parsed, i);
182 if (ext->ext_type == CERTEXT_SIGNED_WITH_KEY) {
187 memcpy(cert->
signing_key.pubkey, ext->un_signing_key, 32);
188 }
else if (ext->ext_flags & CERTEXT_FLAG_AFFECTS_VALIDATION) {
199 ed25519_cert_free(parsed);
214 time_t *expiration_out)
224 checkable_out->
pubkey = pubkey;
227 checkable_out->
len = signed_len;
231 if (expiration_out) {
232 *expiration_out = MIN(*expiration_out, cert->
valid_until);
249 time_t expires = TIME_MAX;
254 if (now && now > expires) {
285 }
else if (cert->
sig_ok) {
317 if (cert1 == NULL && cert2 == NULL)
319 if (!cert1 || !cert2)
324 #define RSA_ED_CROSSCERT_PREFIX "Tor TLS RSA/Ed25519 cross-certificate"
338 tor_assert_nonfatal(expires >= 15 * 365 * 86400);
342 rsa_ed_crosscert_t *cc = rsa_ed_crosscert_new();
344 cc->expiration = (uint32_t) CEIL_DIV(expires, 3600);
348 ssize_t alloc_sz = rsa_ed_crosscert_encoded_len(cc);
350 res = tor_malloc_zero(alloc_sz);
351 ssize_t sz = rsa_ed_crosscert_encode(res, alloc_sz, cc);
356 strlen(RSA_ED_CROSSCERT_PREFIX));
358 const int signed_part_len = 32 + 4;
366 (
char*)rsa_ed_crosscert_getarray_sig(cc),
367 rsa_ed_crosscert_getlen_sig(cc),
368 (
char*)digest,
sizeof(digest));
371 cc->sig_len = siglen;
372 rsa_ed_crosscert_setlen_sig(cc, siglen);
374 sz = rsa_ed_crosscert_encode(res, alloc_sz, cc);
375 rsa_ed_crosscert_free(cc);
392 const size_t crosscert_len,
395 const time_t reject_if_expired_before))
397 rsa_ed_crosscert_t *cc = NULL;
400 #define ERR(code, s) \
402 log_fn(LOG_PROTOCOL_WARN, LD_PROTOCOL, \
403 "Received a bad RSA->Ed25519 crosscert: %s", \
415 ssize_t parsed_len = rsa_ed_crosscert_parse(&cc, crosscert, crosscert_len);
416 if (parsed_len < 0 || crosscert_len != (
size_t)parsed_len) {
417 ERR(-2,
"Unparseable or overlong crosscert");
420 if (
tor_memneq(rsa_ed_crosscert_getarray_ed_key(cc),
423 ERR(-3,
"Crosscert did not match Ed25519 key");
426 const uint32_t expiration_date = rsa_ed_crosscert_get_expiration(cc);
427 const uint64_t expiration_time = ((uint64_t)expiration_date) * 3600;
429 if (reject_if_expired_before < 0 ||
430 expiration_time < (uint64_t)reject_if_expired_before) {
431 ERR(-4,
"Crosscert is expired");
434 const uint8_t *eos = rsa_ed_crosscert_get_end_of_signed(cc);
435 const uint8_t *sig = rsa_ed_crosscert_getarray_sig(cc);
436 const uint8_t siglen = rsa_ed_crosscert_get_sig_len(cc);
438 tor_assert((
size_t)(eos - crosscert) <= crosscert_len);
439 tor_assert(siglen == rsa_ed_crosscert_getlen_sig(cc));
445 strlen(RSA_ED_CROSSCERT_PREFIX));
453 (
char*)signed_,
sizeof(signed_),
456 ERR(-5,
"Bad signature, or length of signed data not as expected");
460 ERR(-6,
"The signature was good, but it didn't match the data");
465 rsa_ed_crosscert_free(cc);
485 tor_x509_cert_free(certs->
id_cert);
492 memwipe(certs, 0xBD,
sizeof(*certs));
499 log_fn(severity, LD_PROTOCOL, \
500 "Received a bad CERTS cell: %s", \
506 or_handshake_certs_rsa_ok(
int severity,
511 tor_x509_cert_t *link_cert = certs->
link_cert;
512 tor_x509_cert_t *auth_cert = certs->
auth_cert;
513 tor_x509_cert_t *id_cert = certs->
id_cert;
516 if (! (id_cert && link_cert))
517 ERR(
"The certs we wanted (ID, Link) were missing");
518 if (! tor_tls_cert_matches_key(tls, link_cert))
519 ERR(
"The link certificate didn't match the TLS public key");
521 ERR(
"The link certificate was not valid");
523 ERR(
"The ID certificate was not valid");
525 if (! (id_cert && auth_cert))
526 ERR(
"The certs we wanted (ID, Auth) were missing");
528 ERR(
"The authentication certificate was not valid");
530 ERR(
"The ID certificate was not valid");
547 unsigned n_checkable = 0;
548 time_t expiration = TIME_MAX;
550 #define ADDCERT(cert, pk) \
552 tor_assert(n_checkable < ARRAY_LENGTH(check)); \
553 if (tor_cert_get_checkable_sig(&check[n_checkable++], cert, pk, \
555 ERR("Could not get checkable cert."); \
559 ERR(
"No Ed25519 signing key");
565 ERR(
"No Ed25519 link key");
569 if (BUG(!peer_cert)) {
573 ERR(
"No x509 peer cert");
577 int okay =
tor_memeq(peer_cert_digests->
d[DIGEST_SHA256],
580 tor_x509_cert_free(peer_cert);
582 ERR(
"Link certificate does not match TLS certificate");
589 ERR(
"No Ed25519 link authentication key");
593 if (expiration < now) {
594 ERR(
"At least one certificate expired.");
604 tor_x509_cert_t *rsa_id_cert = certs->
id_cert;
606 ERR(
"Missing legacy RSA ID certificate");
609 ERR(
"The legacy RSA ID certificate was not valid");
612 ERR(
"Missing RSA->Ed25519 crosscert");
616 ERR(
"RSA ID cert had no RSA key");
624 crypto_pk_free(rsa_id_key);
625 ERR(
"Invalid RSA->Ed25519 crosscert");
627 crypto_pk_free(rsa_id_key);
636 ERR(
"At least one Ed25519 certificate was badly signed");
649 const uint8_t *rsa_id_digest))
656 (
const char*)crosscert,
662 log_warn(
LD_DIR,
"Short signature on cross-certification with TAP key");
668 log_warn(
LD_DIR,
"Incorrect cross-certification with TAP key");
717 if (or_handshake_certs_rsa_ok(severity, certs, tls, now)) {
728 tor_cert_encode_ed22519(
const tor_cert_t *cert,
char **cert_str_out)
731 char *ed_cert_b64 = NULL;
732 size_t ed_cert_b64_len;
739 BASE64_ENCODE_MULTILINE) + 1;
740 ed_cert_b64 = tor_malloc_zero(ed_cert_b64_len);
745 BASE64_ENCODE_MULTILINE) < 0) {
747 log_err(
LD_BUG,
"Couldn't base64-encode ed22519 cert!");
754 "-----BEGIN ED25519 CERT-----\n"
756 "-----END ED25519 CERT-----",
int base64_encode(char *dest, size_t destlen, const char *src, size_t srclen, int flags)
size_t base64_encode_size(size_t srclen, int flags)
Header file for config.c.
void crypto_digest_get_digest(crypto_digest_t *digest, char *out, size_t out_len)
crypto_digest_t * crypto_digest256_new(digest_algorithm_t algorithm)
#define crypto_digest_free(d)
void crypto_digest_add_bytes(crypto_digest_t *digest, const char *data, size_t len)
int ed25519_checksig_batch(int *okay_out, const ed25519_checkable_t *checkable, int n_checkable)
int ed25519_sign(ed25519_signature_t *signature_out, const uint8_t *msg, size_t len, const ed25519_keypair_t *keypair)
size_t crypto_pk_keysize(const crypto_pk_t *env)
int crypto_pk_private_sign(const crypto_pk_t *env, char *to, size_t tolen, const char *from, size_t fromlen)
int crypto_pk_public_checksig(const crypto_pk_t *env, char *to, size_t tolen, const char *from, size_t fromlen)
void memwipe(void *mem, uint8_t byte, size_t sz)
Common functions for cryptographic routines.
int tor_memeq(const void *a, const void *b, size_t sz)
#define tor_memneq(a, b, sz)
Master header file for Tor-specific functionality.
OR handshake certs structure.
int tor_asprintf(char **strp, const char *fmt,...)
char d[N_COMMON_DIGEST_ALGORITHMS][DIGEST256_LEN]
const ed25519_public_key_t * pubkey
ed25519_signature_t signature
struct tor_cert_st * ed_id_sign
struct tor_cert_st * ed_sign_link
uint8_t * ed_rsa_crosscert
struct tor_x509_cert_t * link_cert
struct tor_cert_st * ed_sign_auth
size_t ed_rsa_crosscert_len
struct tor_x509_cert_t * auth_cert
struct tor_x509_cert_t * id_cert
ed25519_public_key_t signing_key
ed25519_public_key_t signed_key
unsigned signing_key_included
#define MOCK_IMPL(rv, funcname, arglist)
void tor_cert_free_(tor_cert_t *cert)
ssize_t tor_make_rsa_ed25519_crosscert(const ed25519_public_key_t *ed_key, const crypto_pk_t *rsa_key, time_t expires, uint8_t **cert)
int rsa_ed25519_crosscert_check(const uint8_t *crosscert, const size_t crosscert_len, const crypto_pk_t *rsa_id_key, const ed25519_public_key_t *master_key, const time_t reject_if_expired_before)
or_handshake_certs_t * or_handshake_certs_new(void)
void or_handshake_certs_free_(or_handshake_certs_t *certs)
int tor_cert_checksig(tor_cert_t *cert, const ed25519_public_key_t *pubkey, time_t now)
int or_handshake_certs_ed25519_ok(int severity, or_handshake_certs_t *certs, tor_tls_t *tls, time_t now)
int tor_cert_opt_eq(const tor_cert_t *cert1, const tor_cert_t *cert2)
tor_cert_t * tor_cert_create_raw(const ed25519_keypair_t *signing_key, uint8_t cert_type, uint8_t signed_key_type, const uint8_t signed_key_info[32], time_t now, time_t lifetime, uint32_t flags)
int tor_cert_eq(const tor_cert_t *cert1, const tor_cert_t *cert2)
const char * tor_cert_describe_signature_status(const tor_cert_t *cert)
tor_cert_t * tor_cert_dup(const tor_cert_t *cert)
tor_cert_t * tor_cert_parse(const uint8_t *encoded, const size_t len)
int tor_cert_get_checkable_sig(ed25519_checkable_t *checkable_out, const tor_cert_t *cert, const ed25519_public_key_t *pubkey, time_t *expiration_out)
int check_tap_onion_key_crosscert(const uint8_t *crosscert, int crosscert_len, const crypto_pk_t *onion_pkey, const ed25519_public_key_t *master_id_pkey, const uint8_t *rsa_id_digest)
void or_handshake_certs_check_both(int severity, or_handshake_certs_t *certs, tor_tls_t *tls, time_t now, const ed25519_public_key_t **ed_id_out, const common_digests_t **rsa_id_out)
tor_cert_t * tor_cert_create_ed25519(const ed25519_keypair_t *signing_key, uint8_t cert_type, const ed25519_public_key_t *signed_key, time_t now, time_t lifetime, uint32_t flags)
struct tor_x509_cert_t * tor_tls_get_peer_cert(tor_tls_t *tls)
int fast_mem_is_zero(const char *mem, size_t len)
#define ED25519_PUBKEY_LEN
crypto_pk_t * tor_tls_cert_get_key(tor_x509_cert_t *cert)
const common_digests_t * tor_x509_cert_get_cert_digests(const tor_x509_cert_t *cert)
int tor_tls_cert_is_valid(int severity, const tor_x509_cert_t *cert, const tor_x509_cert_t *signing_cert, time_t now, int check_rsa_1024)
const common_digests_t * tor_x509_cert_get_id_digests(const tor_x509_cert_t *cert)