iPXE
channel.h File Reference

Secure channel abstraction. More...

#include <stdint.h>
#include <ipxe/crypto.h>
#include <ipxe/x509.h>
#include <ipxe/sha256.h>

Go to the source code of this file.

Data Structures

struct  secure_channel_properties
 Secure channel properties. More...
struct  secure_pipe
 A secure channel transmit or receive pipe. More...
struct  secure_channel
 A secure channel. More...
struct  secure_preshared_identity
 A pre-shared bound peer identity. More...
struct  secure_channel_operations
 Secure channel operations. More...

Macros

#define channel_ephemeral_algorithm   sha256_algorithm
 Ephemeral master secret digest algorithm.

Functions

 FILE_LICENCE (GPL2_OR_LATER_OR_UBDL)
 FILE_SECBOOT (PERMITTED)
static void channel_init (struct secure_channel *channel, struct secure_channel_operations *op)
 Initialise secure channel.
static int channel_is_established (struct secure_channel *channel)
 Check if secure channel has been established.
static void channel_clear_preshared (struct secure_preshared_identity *psid)
 Clear pre-shared bound peer identity.
void channel_ephemeral (struct secure_channel *channel, const void *info, size_t info_len, void *out, size_t len)
 Generate ephemeral secret.
void channel_ephemeral_label (struct secure_channel *channel, const char *label, void *out, size_t len)
 Generate labelled ephemeral secret.
void channel_unkey (struct secure_channel *channel)
 Clear shared secret.
int channel_key_share (struct secure_channel *channel, struct exchange_algorithm *exchange, void *public)
 Share public key.
int channel_key_agree (struct secure_channel *channel, struct exchange_algorithm *exchange, const void *partner)
 Agree shared secret.
int channel_bind_verify (struct secure_channel *channel, struct x509_certificate *identity, struct pubkey_algorithm *pubkey, struct digest_algorithm *digest, const void *value, const struct asn1_cursor *signature)
 Bind peer identity via ephemeral public key signature verification.
int channel_bind_encrypt (struct secure_channel *channel, struct x509_certificate *identity, struct exchange_algorithm *exchange, struct pubkey_algorithm *pubkey, struct asn1_builder *ciphertext)
 Bind peer identity via shared secret encryption.
int channel_save (struct secure_channel *channel, struct secure_preshared_identity *psid)
 Save a pre-shared key.
int channel_load (struct secure_channel *channel, struct secure_preshared_identity *psid)
 Load a pre-shared key.
int channel_confirm (struct secure_channel *channel, const void *auth, size_t len)
 Confirm peer identity.
int channel_establish (struct secure_channel *channel, const char *name, struct x509_root *root)
 Establish channel as trusted for application data.
int channel_set_cipher (struct secure_channel *channel, struct secure_pipe *pipe, struct cipher_algorithm *cipher, const void *key, size_t len)
 Set cipher algorithm and key.
int channel_open (struct secure_channel *channel)
 Open secure channel.
void channel_reopen (struct secure_channel *channel)
 Reopen secure channel.
void channel_close (struct secure_channel *channel)
 Close secure channel.

Variables

struct cipher_algorithm channel_dead_cipher
 Dead cipher.

Detailed Description

Secure channel abstraction.

Definition in file channel.h.

Macro Definition Documentation

◆ channel_ephemeral_algorithm

#define channel_ephemeral_algorithm   sha256_algorithm

Ephemeral master secret digest algorithm.

Definition at line 19 of file channel.h.

Referenced by channel_ephemeral(), and channel_ephemeral_init().

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL )

◆ FILE_SECBOOT()

FILE_SECBOOT ( PERMITTED )

◆ channel_init()

void channel_init ( struct secure_channel * channel,
struct secure_channel_operations * op )
inlinestatic

Initialise secure channel.

Parameters
channelSecure channel
opChannel operations

Definition at line 256 of file channel.h.

257 {
258
259 channel->op = op;
260 channel->tx.cipher = &channel_dead_cipher;
261 channel->rx.cipher = &channel_dead_cipher;
262}
struct cipher_algorithm channel_dead_cipher
Dead cipher.
Definition channel.c:1073
uint32_t channel
RNDIS channel.
Definition netvsc.h:3
static uint16_t struct vmbus_xfer_pages_operations * op
Definition netvsc.h:327

References channel, channel_dead_cipher, and op.

Referenced by add_tls().

◆ channel_is_established()

int channel_is_established ( struct secure_channel * channel)
inlinestatic

Check if secure channel has been established.

Parameters
channelSecure channel
Return values
is_establishedChannel has been established

Definition at line 271 of file channel.h.

271 {
272
273 return ( channel->props.established != NULL );
274}
#define NULL
NULL pointer (VOID *).
Definition Base.h:321

References channel, and NULL.

Referenced by tls_channel_save(), and tls_ready().

◆ channel_clear_preshared()

void channel_clear_preshared ( struct secure_preshared_identity * psid)
inlinestatic

Clear pre-shared bound peer identity.

Parameters
psidPre-shared identity

Definition at line 282 of file channel.h.

282 {
283
284 x509_put ( psid->bound );
285 psid->bound = NULL;
286}
struct x509_certificate * bound
Bound peer identity.
Definition channel.h:99
static void x509_put(struct x509_certificate *cert)
Drop reference to X.509 certificate.
Definition x509.h:278

References secure_preshared_identity::bound, NULL, and x509_put().

Referenced by channel_save(), and free_tls_session().

◆ channel_ephemeral()

void channel_ephemeral ( struct secure_channel * channel,
const void * info,
size_t info_len,
void * out,
size_t len )
extern

Generate ephemeral secret.

Parameters
channelSecure channel
infoAdditional information
info_lenLength of additional information
outEphemeral secret to fill in
lenLength of ephemeral secret

Definition at line 195 of file channel.c.

196 {
198
199 /* Additional info should always be provided */
200 assert ( info != NULL );
201 assert ( info_len > 0 );
202
203 /* Generate from ephemeral master secret and additional information */
204 hkdf_expand ( digest, channel->ephemeral, info, info_len, out, len );
205}
__be32 out[4]
Definition CIB_PRM.h:8
u32 info
Definition ar9003_mac.h:0
#define assert(condition)
Assert a condition at run-time.
Definition assert.h:61
#define channel_ephemeral_algorithm
Ephemeral master secret digest algorithm.
Definition channel.h:19
ring len
Length.
Definition dwmac.h:226
void hkdf_expand(struct digest_algorithm *digest, const void *prk, const void *info, size_t info_len, void *out, size_t len)
Expand pseudorandom key.
Definition hkdf.c:95
uint8_t info_len
Reject information length.
Definition ib_mad.h:7
A message digest algorithm.
Definition crypto.h:19

References assert, channel, channel_ephemeral_algorithm, hkdf_expand(), info, info_len, len, NULL, and out.

Referenced by channel_ephemeral_label(), and tls_send_record().

◆ channel_ephemeral_label()

void channel_ephemeral_label ( struct secure_channel * channel,
const char * label,
void * out,
size_t len )
extern

Generate labelled ephemeral secret.

Parameters
channelSecure channel
labelAdditional information string
outEphemeral secret to fill in
lenLength of ephemeral secret

Definition at line 215 of file channel.c.

216 {
217
218 /* Generate from ephemeral master secret and label */
220 DBGC2 ( channel, "CHANNEL %p ephemeral \"%s\":\n", channel, label );
221 DBGC2_HDA ( channel, 0, out, len );
222}
void channel_ephemeral(struct secure_channel *channel, const void *info, size_t info_len, void *out, size_t len)
Generate ephemeral secret.
Definition channel.c:195
#define DBGC2(...)
Definition compiler.h:547
#define DBGC2_HDA(...)
Definition compiler.h:548
size_t strlen(const char *src)
Get length of string.
Definition string.c:244
A text label widget.
Definition label.h:16

References channel, channel_ephemeral(), DBGC2, DBGC2_HDA, len, out, and strlen().

Referenced by channel_ephemeral_replace(), channel_key_private(), tls_nonce(), and tls_session().

◆ channel_unkey()

void channel_unkey ( struct secure_channel * channel)
extern

Clear shared secret.

Parameters
channelSecure channel

Definition at line 273 of file channel.c.

273 {
274
275 /* Key binding is defined only for the current shared secret,
276 * and so any existing bound peer identity must be cleared.
277 */
279
280 /* Clear shared key */
281 channel->props.keyed = 0;
282
283 /* Reset the key schedule */
284 channel->op->reset ( channel );
285}
static void channel_unbind(struct secure_channel *channel)
Clear bound peer identity.
Definition channel.c:545

References channel, and channel_unbind().

Referenced by channel_bind_encrypt(), channel_close(), channel_key(), channel_load(), channel_open(), channel_reopen(), and tls_clear_digest().

◆ channel_key_share()

int channel_key_share ( struct secure_channel * channel,
struct exchange_algorithm * exchange,
void * public )
extern

Share public key.

Parameters
channelSecure channel
exchangeKey exchange algorithm
publicPublic key to fill in
Return values
rcReturn status code

Definition at line 320 of file channel.c.

321 {
322 size_t privsize = exchange->privsize;
323 size_t pubsize = exchange->pubsize;
324 uint8_t private[privsize];
325 int rc;
326
327 /* (Re)generate private key */
328 channel_key_private ( channel, exchange, private );
329
330 /* Generate public key */
331 if ( ( rc = exchange_share ( exchange, private, public ) ) != 0 ) {
332 DBGC ( channel, "CHANNEL %p could not share \"%s\": %s\n",
333 channel, exchange->name, strerror ( rc ) );
334 goto err_share;
335 }
336
337 /* Show public key (for debugging) */
338 DBGC2 ( channel, "CHANNEL %p sharing \"%s\":\n",
339 channel, exchange->name );
340 DBGC2_HDA ( channel, 0, public, pubsize );
341
342 err_share:
343 /* Erase private key */
344 memset ( private, 0, sizeof ( private ) );
345 return rc;
346}
struct arbelprm_rc_send_wqe rc
Definition arbel.h:3
unsigned char uint8_t
Definition stdint.h:10
static void channel_key_private(struct secure_channel *channel, struct exchange_algorithm *exchange, void *private)
Generate private key.
Definition channel.c:294
#define DBGC(...)
Definition compiler.h:530
static int exchange_share(struct exchange_algorithm *exchange, const void *private, void *public)
Definition crypto.h:397
void * memset(void *dest, int character, size_t len) __nonnull
char * strerror(int errno)
Retrieve string representation of error number.
Definition strerror.c:79
size_t privsize
Private key size.
Definition crypto.h:214
size_t pubsize
Public key size.
Definition crypto.h:216
const char * name
Algorithm name.
Definition crypto.h:212

References channel, channel_key_private(), DBGC, DBGC2, DBGC2_HDA, exchange_share(), memset(), exchange_algorithm::name, exchange_algorithm::privsize, exchange_algorithm::pubsize, rc, and strerror().

Referenced by tls_key_share().

◆ channel_key_agree()

int channel_key_agree ( struct secure_channel * channel,
struct exchange_algorithm * exchange,
const void * partner )
extern

Agree shared secret.

Parameters
channelSecure channel
exchangeKey exchange algorithm
partnerPartner public key
Return values
rcReturn status code

Definition at line 424 of file channel.c.

426 {
427 size_t sharedsize = exchange->sharedsize;
428 size_t pubsize = exchange->pubsize;
429 void *tmp;
430 int rc;
431
432 /* Show partner public key (for debugging) */
433 DBGC2 ( channel, "CHANNEL %p partner \"%s\":\n",
434 channel, exchange->name );
435 DBGC2_HDA ( channel, 0, partner, pubsize );
436
437 /* Allocate space for shared secret (may be too large for stack) */
438 tmp = zalloc ( sharedsize );
439 if ( ! tmp ) {
440 rc = -ENOMEM;
441 goto err_alloc;
442 }
443
444 /* Generate and apply shared secret */
445 if ( ( rc = channel_key ( channel, exchange, partner, tmp ) ) != 0 )
446 goto err_key;
447
448 err_key:
449 /* Erase shared secret */
450 zfree ( tmp );
451 err_alloc:
452 return rc;
453}
static int channel_key(struct secure_channel *channel, struct exchange_algorithm *exchange, const void *partner, void *shared)
Generate and apply shared secret.
Definition channel.c:357
struct eth_slow_lacp_entity_tlv partner
Partner information.
Definition eth_slow.h:5
#define ENOMEM
Not enough space.
Definition errno.h:578
unsigned long tmp
Definition linux_pci.h:65
void * zalloc(size_t size)
Allocate cleared memory.
Definition malloc.c:718
void zfree(void *ptr)
Clear and free memory.
Definition malloc.c:738
size_t sharedsize
Shared secret size.
Definition crypto.h:218

References channel, channel_key(), DBGC2, DBGC2_HDA, ENOMEM, exchange_algorithm::name, partner, exchange_algorithm::pubsize, rc, exchange_algorithm::sharedsize, tmp, zalloc(), and zfree().

Referenced by tls_key_agree().

◆ channel_bind_verify()

int channel_bind_verify ( struct secure_channel * channel,
struct x509_certificate * identity,
struct pubkey_algorithm * pubkey,
struct digest_algorithm * digest,
const void * value,
const struct asn1_cursor * signature )
extern

Bind peer identity via ephemeral public key signature verification.

Parameters
channelSecure channel
identityIdentity to be bound
pubkeyPublic-key algorithm
digestDigest algorithm
valueDigest value (must cover peer's ephemeral public key)
signatureSignature
Return values
rcReturn status code

The peer may delegate authority to the shared secret by signing a digest that covers at least its own ephemeral public key (e.g. the Diffie-Hellman parameters provided in a ServerKeyExchange record) and a challenge nonce (e.g. the TLS client random bytes).

The consumer asserts to the secure channel that the digest covers at least the peer's ephemeral public key and a nonce. The digest may cover arbitrary additional information (e.g. the entire transcript hash as signed by a CertificateVerify record).

This assertion is an unverifiable promise made by the consumer: there is no way for the secure channel itself to determine what is covered by the digest.

Definition at line 611 of file channel.c.

615 {
616 const struct asn1_cursor *key = &identity->subject.public_key.raw;
617 int rc;
618
619 /* Verify signature */
620 if ( ( rc = pubkey_verify ( pubkey, key, digest, value,
621 signature ) ) != 0 ) {
622 DBGC ( channel, "CHANNEL %p could not verify binding: %s\n",
623 channel, strerror ( rc ) );
624 return rc;
625 }
626
627 /* Bind to the identity that signed the shared secret */
628 if ( ( rc = channel_bind ( channel, identity ) ) != 0 )
629 return rc;
630
631 return 0;
632}
u8 signature
CPU signature.
Definition CIB_PRM.h:7
union @162305117151260234136356364136041353210355154177 key
pseudo_bit_t value[0x00020]
Definition arbel.h:2
static int channel_bind(struct secure_channel *channel, struct x509_certificate *identity)
Set bound peer identity.
Definition channel.c:565
static int pubkey_verify(struct pubkey_algorithm *pubkey, const struct asn1_cursor *key, struct digest_algorithm *digest, const void *value, const struct asn1_cursor *signature)
Definition crypto.h:383
An ASN.1 object cursor.
Definition asn1.h:21
struct x509_subject subject
Subject.
Definition x509.h:245
struct asn1_cursor raw
Raw public key information.
Definition x509.h:52
struct x509_public_key public_key
Public key information.
Definition x509.h:66

References channel, channel_bind(), DBGC, key, pubkey_verify(), x509_subject::public_key, x509_public_key::raw, rc, signature, strerror(), x509_certificate::subject, and value.

Referenced by tls_new_server_key_exchange().

◆ channel_bind_encrypt()

int channel_bind_encrypt ( struct secure_channel * channel,
struct x509_certificate * identity,
struct exchange_algorithm * exchange,
struct pubkey_algorithm * pubkey,
struct asn1_builder * ciphertext )
extern

Bind peer identity via shared secret encryption.

Parameters
channelSecure channel
identityIdentity to be bound
exchangeKey exchange algorithm
pubkeyPublic-key algorithm
ciphertextEncrypted shared secret
Return values
rcReturn status code

The local endpoint may delegate authority to the shared secret by encrypting a unilaterally chosen shared secret (e.g. a classic TLS static RSA pre-master secret).

Definition at line 648 of file channel.c.

652 {
653 const struct asn1_cursor *key = &identity->subject.public_key.raw;
654 size_t sharedsize = exchange->sharedsize;
655 struct asn1_cursor plaintext;
656 void *tmp;
657 int rc;
658
659 /* Allocate space for shared secret (may be too large for stack) */
660 tmp = zalloc ( sharedsize );
661 if ( ! tmp ) {
662 rc = -ENOMEM;
663 goto err_alloc;
664 }
665 plaintext.data = tmp;
666 plaintext.len = sharedsize;
667
668 /* Generate unencrypted shared secret */
669 if ( ( rc = channel_key_transport ( channel, exchange, tmp ) ) != 0 )
670 goto err_transport;
671
672 /* Encrypt shared secret */
673 if ( ( rc = pubkey_encrypt ( pubkey, key, &plaintext,
674 ciphertext ) ) != 0 ) {
675 DBGC ( channel, "CHANNEL %p could not encrypt \"%s\": %s\n",
676 channel, exchange->name, strerror ( rc ) );
677 goto err_encrypt;
678 }
679
680 /* Bind to the identity that can decrypt the shared secret */
681 if ( ( rc = channel_bind ( channel, identity ) ) != 0 )
682 goto err_bind;
683
684 err_bind:
685 err_encrypt:
686 err_transport:
687 /* Clear the generated shared secret on any error */
688 if ( rc != 0 )
690 /* Erase unencrypted shared secret */
691 zfree ( tmp );
692 err_alloc:
693 return rc;
694}
static int channel_key_transport(struct secure_channel *channel, struct exchange_algorithm *exchange, void *shared)
Transport shared secret.
Definition channel.c:467
void channel_unkey(struct secure_channel *channel)
Clear shared secret.
Definition channel.c:273
static int pubkey_encrypt(struct pubkey_algorithm *pubkey, const struct asn1_cursor *key, const struct asn1_cursor *plaintext, struct asn1_builder *ciphertext)
Definition crypto.h:362

References channel, channel_bind(), channel_key_transport(), channel_unkey(), asn1_cursor::data, DBGC, ENOMEM, key, asn1_cursor::len, exchange_algorithm::name, pubkey_encrypt(), x509_subject::public_key, x509_public_key::raw, rc, exchange_algorithm::sharedsize, strerror(), x509_certificate::subject, tmp, zalloc(), and zfree().

Referenced by tls_key_encrypt().

◆ channel_save()

int channel_save ( struct secure_channel * channel,
struct secure_preshared_identity * psid )
extern

Save a pre-shared key.

Parameters
channelSecure channel
psidPre-shared bound peer identity
Return values
rcReturn status code

Definition at line 738 of file channel.c.

739 {
740 struct x509_certificate *identity;
741 int rc;
742
743 /* Clear any existing pre-shared bound peer identity */
745
746 /* Fail if there is no bound peer identity to save */
747 identity = channel->props.bound;
748 if ( ! identity ) {
749 DBGC ( channel, "CHANNEL %p cannot create pre-shared key "
750 "for unbound peer\n", channel );
751 return -EPROTO_NOT_BOUND;
752 }
753
754 /* Fail if consumer does not support pre-shared keys */
755 if ( ! channel->op->save ) {
756 DBGC ( channel, "CHANNEL %p does not support pre-shared "
757 "keys\n", channel );
758 return -ENOTSUP;
759 }
760
761 /* Save pre-shared key */
762 if ( ( rc = channel->op->save ( channel, psid ) ) != 0 ) {
763 DBGC ( channel, "CHANNEL %p could not save pre-shared "
764 "key: %s\n", channel, strerror ( rc ) );
765 return rc;
766 }
767
768 /* Record pre-shared bound peer identity */
769 psid->bound = x509_get ( identity );
770 DBGC ( channel, "CHANNEL %p key material saved for \"%s\"\n",
771 channel, x509_name ( identity ) );
772
773 return 0;
774}
#define EPROTO_NOT_BOUND
Definition channel.c:126
static void channel_clear_preshared(struct secure_preshared_identity *psid)
Clear pre-shared bound peer identity.
Definition channel.h:282
#define ENOTSUP
Operation not supported.
Definition errno.h:633
An X.509 certificate.
Definition x509.h:216
const char * x509_name(struct x509_certificate *cert)
Get X.509 certificate display name.
Definition x509.c:147
static struct x509_certificate * x509_get(struct x509_certificate *cert)
Get reference to X.509 certificate.
Definition x509.h:267

References secure_preshared_identity::bound, channel, channel_clear_preshared(), DBGC, ENOTSUP, EPROTO_NOT_BOUND, rc, strerror(), x509_get(), and x509_name().

Referenced by tls_save().

◆ channel_load()

int channel_load ( struct secure_channel * channel,
struct secure_preshared_identity * psid )
extern

Load a pre-shared key.

Parameters
channelSecure channel
psidPre-shared bound peer identity
Return values
rcReturn status code

Definition at line 783 of file channel.c.

784 {
785 struct x509_certificate *identity;
786 int rc;
787
788 /* Clear any existing shared secret */
790
791 /* Fail if there is no bound peer identity to resume */
792 identity = psid->bound;
793 if ( ! identity ) {
794 DBGC ( channel, "CHANNEL %p cannot resume from empty "
795 "pre-shared key\n", channel );
797 goto err_empty;
798 }
799
800 /* Fail if consumer does not support pre-shared keys */
801 if ( ! channel->op->load ) {
802 DBGC ( channel, "CHANNEL %p does not support pre-shared "
803 "keys\n", channel );
804 rc = -ENOTSUP;
805 goto err_unsupported;
806 }
807
808 /* Load pre-shared key */
809 if ( ( rc = channel->op->load ( channel, psid ) ) != 0 ) {
810 DBGC ( channel, "CHANNEL %p could not load pre-shared key: "
811 "%s\n", channel, strerror ( rc ) );
812 goto err_load;
813 }
814
815 /* Channel now possesses a shared secret */
816 channel->props.keyed = 1;
817 DBGC ( channel, "CHANNEL %p key material obtained from pre-shared "
818 "key\n", channel );
819
820 /* Bind to the identity that was bound to the pre-shared key */
821 if ( ( rc = channel_bind ( channel, identity ) ) != 0 )
822 goto err_bind;
823
824 return 0;
825
826 err_bind:
827 err_load:
828 err_unsupported:
829 err_empty:
831 return rc;
832}

References secure_preshared_identity::bound, channel, channel_bind(), channel_unkey(), DBGC, ENOTSUP, EPROTO_NOT_BOUND, rc, and strerror().

Referenced by tls_resume().

◆ channel_confirm()

int channel_confirm ( struct secure_channel * channel,
const void * auth,
size_t len )
extern

Confirm peer identity.

Parameters
channelSecure channel
authAuthenticator value
lenLength of authenticator value
Return values
rcReturn status code

The consumer asserts to the secure channel that the authenticator value was received after the receive pipe was transitioned to a cipher capable of providing confidentiality.

This assertion is an unverifiable promise made by the consumer: there is no way for the secure channel itself to determine when the authenticator value was received.

Definition at line 896 of file channel.c.

897 {
898 struct x509_certificate *identity;
899 int rc;
900
901 /* Clear any existing confirmed peer identity */
903
904 /* Fail if there is no bound peer identity to authenticate */
905 identity = channel->props.bound;
906 if ( ! identity ) {
907 DBGC ( channel, "CHANNEL %p cannot authenticate unbound "
908 "peer\n", channel );
909 return -EPROTO_NOT_BOUND;
910 }
911
912 /* Sanity check: binding is not possible without keying */
913 assert ( channel->props.keyed );
914
915 /* Require key confirmation over a confidential channel */
916 if ( ! channel->rx.cipher->confidential ) {
917 DBGC ( channel, "CHANNEL %p cannot confirm key with a "
918 "non-confidential cipher\n", channel );
920 }
921
922 /* Verify authentication data */
923 if ( ( rc = channel->op->verify ( channel, auth, len ) ) != 0 ) {
924 DBGC ( channel, "CHANNEL %p failed to authenticate: %s\n",
925 channel, strerror ( rc ) );
926 return rc;
927 }
928
929 /* Record bound peer identity as confirmed peer identity */
930 channel->props.confirmed = x509_get ( identity );
931 DBGC ( channel, "CHANNEL %p key material confirmed for \"%s\"\n",
932 channel, x509_name ( identity ) );
933
934 return 0;
935}
#define EPERM_NOT_CONFIDENTIAL
Definition channel.c:117
static void channel_unconfirm(struct secure_channel *channel)
Clear confirmed peer identity.
Definition channel.c:867

References assert, channel, channel_unconfirm(), DBGC, EPERM_NOT_CONFIDENTIAL, EPROTO_NOT_BOUND, len, rc, strerror(), x509_get(), and x509_name().

Referenced by tls_new_finished().

◆ channel_establish()

int channel_establish ( struct secure_channel * channel,
const char * name,
struct x509_root * root )
extern

Establish channel as trusted for application data.

Parameters
channelSecure channel
nameRequired peer identity name
rootRoot certificate list, or NULL to use default
Return values
rcReturn status code

Definition at line 986 of file channel.c.

987 {
988 struct x509_certificate *identity;
989 int rc;
990
991 /* Clear any existing established peer identity */
993
994 /* Fail if there is no confirmed peer identity to establish */
995 identity = channel->props.confirmed;
996 if ( ! identity ) {
997 DBGC ( channel, "CHANNEL %p cannot establish unconfirmed "
998 "peer\n", channel );
999 return -EPROTO_NOT_CONFIRMED;
1000 }
1001
1002 /* Sanity check: confirmation is not possible without binding */
1003 assert ( channel->props.bound == identity );
1004 assert ( channel->props.keyed );
1005
1006 /* Fail if ciphers are still operating in plaintext mode */
1007 if ( ! ( channel->tx.cipher->confidential &&
1008 channel->rx.cipher->confidential ) ) {
1009 DBGC ( channel, "CHANNEL %p cannot establish channel with a "
1010 "non-confidential cipher\n", channel );
1011 return -EPERM_NOT_CONFIDENTIAL;
1012 }
1013
1014 /* Fail if confirmed peer identity name is incorrect */
1015 if ( ( rc = x509_check_name ( identity, name ) ) != 0 ) {
1016 DBGC ( channel, "CHANNEL %p identity \"%s\" does not match "
1017 "\"%s\": %s\n", channel, x509_name ( identity ),
1018 name, strerror ( rc ) );
1019 return rc;
1020 }
1021
1022 /* Fail if confirmed peer identity has not been validated */
1023 if ( ! x509_is_valid ( identity, root ) ) {
1024 DBGC ( channel, "CHANNEL %p identity \"%s\" has not been "
1025 "validated\n", channel, x509_name ( identity ) );
1026 return -EPERM_NOT_VALID;
1027 }
1028
1029 /* Record confirmed peer identity as established peer identity */
1030 channel->props.established = x509_get ( identity );
1031 DBGC ( channel, "CHANNEL %p established for \"%s\"\n",
1032 channel, x509_name ( identity ) );
1033
1034 return 0;
1035}
const char * name
Definition ath9k_hw.c:1986
#define EPROTO_NOT_CONFIRMED
Definition channel.c:129
#define EPERM_NOT_VALID
Definition channel.c:120
static void channel_unestablish(struct secure_channel *channel)
Clear established peer identity.
Definition channel.c:971
struct stp_switch root
Root switch.
Definition stp.h:15
int x509_is_valid(struct x509_certificate *cert, struct x509_root *root)
Check if X.509 certificate is valid.
Definition x509.c:1313
int x509_check_name(struct x509_certificate *cert, const char *name)
Check X.509 certificate name.
Definition x509.c:1564

References assert, channel, channel_unestablish(), DBGC, EPERM_NOT_CONFIDENTIAL, EPERM_NOT_VALID, EPROTO_NOT_CONFIRMED, name, rc, root, strerror(), x509_check_name(), x509_get(), x509_is_valid(), and x509_name().

Referenced by tls_establish().

◆ channel_set_cipher()

int channel_set_cipher ( struct secure_channel * channel,
struct secure_pipe * pipe,
struct cipher_algorithm * cipher,
const void * key,
size_t len )
extern

Set cipher algorithm and key.

Parameters
channelSecure channel
pipeSecure channel pipe
cipherCipher algorithm
keyKey
lenLength of key
Return values
rcReturn status code

The consumer asserts to the secure channel that the key is ultimately derived from the shared secret that was previously provided to the consumer by the secure channel, i.e. that possession of the cipher key implies possession of the shared secret.

This assertion is an unverifiable promise made by the consumer: we can check that a shared secret exists, but there is no way for the secure channel itself to determine how the cipher key is derived.

Definition at line 1136 of file channel.c.

1139 {
1140 int rc;
1141
1142 /* Zero and free any existing cipher context */
1143 channel_clear_cipher ( pipe );
1144
1145 /* Fail if there is no shared secret from which a key could derive */
1146 if ( ! channel->props.keyed ) {
1147 DBGC ( channel, "CHANNEL %p refusing to use definitely "
1148 "non-derived shared secret\n", channel );
1150 goto err_keyed;
1151 }
1152
1153 /* Refuse to explicitly set a non-confidential cipher */
1154 if ( ! cipher->confidential ) {
1155 DBGC ( channel, "CHANNEL %p %s refusing to use "
1156 "non-confidential cipher \"%s\"\n", channel,
1157 channel_pipe_name ( channel, pipe ), cipher->name );
1159 goto err_confidential;
1160 }
1161 pipe->cipher = cipher;
1162
1163 /* Allocate new context */
1164 pipe->ctx = zalloc ( cipher->ctxsize );
1165 if ( ! pipe->ctx ) {
1166 rc = -ENOMEM;
1167 goto err_alloc;
1168 }
1169
1170 /* Set cipher key */
1171 if ( ( rc = cipher_setkey ( cipher, pipe->ctx, key, len ) ) != 0 ) {
1172 DBGC ( channel, "CHANNEL %p %s could not set \"%s\" key: %s\n",
1174 cipher->name, strerror ( rc ) );
1175 goto err_setkey;
1176 }
1177
1178 DBGC ( channel, "CHANNEL %p %s using \"%s\" with %zd-bit key\n",
1180 cipher->name, ( 8 * len ) );
1181 return 0;
1182
1183 err_setkey:
1184 err_alloc:
1185 err_confidential:
1186 err_keyed:
1187 channel_clear_cipher ( pipe );
1188 return rc;
1189}
static const char * channel_pipe_name(struct secure_channel *channel, struct secure_pipe *pipe)
Get pipe name (for debugging).
Definition channel.c:1094
static void channel_clear_cipher(struct secure_pipe *pipe)
Clear cipher algorithm.
Definition channel.c:1106
#define EPROTO_NOT_KEYED
Definition channel.c:123
static int cipher_setkey(struct cipher_algorithm *cipher, void *ctx, const void *key, size_t keylen)
Definition crypto.h:310
const char * name
Algorithm name.
Definition crypto.h:60
int confidential
Cipher is capable of providing confidentiality.
Definition crypto.h:84
size_t ctxsize
Context size.
Definition crypto.h:62
void * ctx
Cipher context.
Definition channel.h:60
struct cipher_algorithm * cipher
Cipher algorithm.
Definition channel.h:58

References channel, channel_clear_cipher(), channel_pipe_name(), secure_pipe::cipher, cipher_setkey(), cipher_algorithm::confidential, secure_pipe::ctx, cipher_algorithm::ctxsize, DBGC, ENOMEM, EPERM_NOT_CONFIDENTIAL, EPROTO_NOT_KEYED, key, len, cipher_algorithm::name, rc, strerror(), and zalloc().

Referenced by tls_change_cipher().

◆ channel_open()

int channel_open ( struct secure_channel * channel)
extern

Open secure channel.

Parameters
channelSecure channel
Return values
rcReturn status code

Definition at line 1205 of file channel.c.

1205 {
1206 int rc;
1207
1208 /* Sanity checks */
1209 assert ( channel != NULL );
1210 assert ( channel->op != NULL );
1211 assert ( channel->op->reset != NULL );
1212 assert ( channel->op->apply != NULL );
1213 assert ( channel->op->verify != NULL );
1214
1215 /* Clear security properties (which should already be clear) */
1216 assert ( channel->props.keyed == 0 );
1217 assert ( channel->props.bound == NULL );
1218 assert ( channel->props.confirmed == NULL );
1219 assert ( channel->props.established == NULL );
1221 assert ( channel->props.keyed == 0 );
1222 assert ( channel->props.bound == NULL );
1223 assert ( channel->props.confirmed == NULL );
1224 assert ( channel->props.established == NULL );
1225
1226 /* Reset ciphers (which should already have no contexts) */
1227 assert ( channel->tx.ctx == NULL );
1228 assert ( channel->rx.ctx == NULL );
1231 assert ( channel->tx.ctx == NULL );
1232 assert ( channel->rx.ctx == NULL );
1233
1234 /* Initialise ephemeral master secret */
1235 if ( ( rc = channel_ephemeral_init ( channel ) ) != 0 )
1236 return rc;
1237
1238 /* Enable initial plaintext ciphers */
1239 channel->tx.cipher = &cipher_null;
1240 channel->rx.cipher = &cipher_null;
1241
1242 DBGC ( channel, "CHANNEL %p opened\n", channel );
1243 return 0;
1244}
static int channel_ephemeral_init(struct secure_channel *channel)
Initialise ephemeral master secret.
Definition channel.c:164
struct cipher_algorithm cipher_null
Definition crypto_null.c:94

References assert, channel, channel_clear_cipher(), channel_ephemeral_init(), channel_unkey(), cipher_null, DBGC, NULL, and rc.

Referenced by add_tls().

◆ channel_reopen()

void channel_reopen ( struct secure_channel * channel)
extern

Reopen secure channel.

Parameters
channelSecure channel

The channel will be returned to a freshly opened state (including a new ephemeral master secret), but with any existing cipher state retained. All security properties will be cleared.

This allows a new secure channel to be established with either or both of the transmit and receive pipes having already transitioned to a cipher capable of providing confidentiality.

The consumer may choose to reopen a fully established channel while leaving the cipher keys intact (as is done in TLS renegotiation), in which case it may choose to treat the channel as remaining established (to the old peer identity) at least until the point that the cipher keys are next changed (and possibly further, depending upon the protocol design). The secure channel itself does not attempt to model any such choice by the consumer: reopening will clear all security properties including the established peer identity.

Definition at line 1269 of file channel.c.

1269 {
1270
1271 /* Clear security properties */
1273 assert ( channel->props.keyed == 0 );
1274 assert ( channel->props.bound == NULL );
1275 assert ( channel->props.confirmed == NULL );
1276 assert ( channel->props.established == NULL );
1277
1278 /* Replace ephemeral master secret
1279 *
1280 * We choose to replace rather than reinitialise the ephemeral
1281 * master secret so that this function may be used from code
1282 * paths that cannot allow for failure (such as when closing
1283 * the channel).
1284 */
1286
1287 DBGC ( channel, "CHANNEL %p reopened\n", channel );
1288}
static void channel_ephemeral_replace(struct secure_channel *channel)
Replace ephemeral master secret.
Definition channel.c:229

References assert, channel, channel_ephemeral_replace(), channel_unkey(), DBGC, and NULL.

Referenced by tls_restart().

◆ channel_close()

void channel_close ( struct secure_channel * channel)
extern

Close secure channel.

Parameters
channelSecure channel

All secret values held by the secure channel will be destroyed, including the ephemeral master secret.

This function may safely be called on a channel that has already been closed.

Definition at line 1301 of file channel.c.

1301 {
1302
1303 /* Clear security properties */
1305 assert ( channel->props.keyed == 0 );
1306 assert ( channel->props.bound == NULL );
1307 assert ( channel->props.confirmed == NULL );
1308 assert ( channel->props.established == NULL );
1309
1310 /* Reset ciphers */
1313 assert ( channel->tx.ctx == NULL );
1314 assert ( channel->rx.ctx == NULL );
1315
1316 /* Replace ephemeral master secret
1317 *
1318 * We choose to replace rather than zero the ephemeral master
1319 * secret. For any channel that has been successfully opened,
1320 * this ensures that an erroneous reuse of the channel after
1321 * it has been closed cannot lead to the use of predictable
1322 * ephemeral secrets (derived from an all-zero value), or to
1323 * reuse of its previous ephemeral secrets.
1324 */
1326
1327 DBGC ( channel, "CHANNEL %p closed\n", channel );
1328}

References assert, channel, channel_clear_cipher(), channel_ephemeral_replace(), channel_unkey(), DBGC, and NULL.

Referenced by add_tls(), and tls_close().

Variable Documentation

◆ channel_dead_cipher

struct cipher_algorithm channel_dead_cipher
extern

Dead cipher.

We activate this cipher (rather than the null cipher) upon any cipher-related failure, to guard against code paths that may fail to check for cipher errors.

Definition at line 1073 of file channel.c.

1073 {
1074 .name = "dead",
1075 .ctxsize = 0,
1076 .blocksize = 1,
1077 .alignsize = 1,
1078 .authsize = 0,
1079 .confidential = 0,
1080 .setkey = cipher_null_setkey,
1081 .setiv = cipher_null_setiv,
1082 .encrypt = channel_dead_crypt,
1083 .decrypt = channel_dead_crypt,
1084 .auth = cipher_null_auth,
1085};
static void channel_dead_crypt(struct cipher_algorithm *cipher __unused, void *ctx __unused, const void *src __unused, void *dst, size_t len)
Encrypt or decrypt data via dead cipher.
Definition channel.c:1054
int cipher_null_setiv(struct cipher_algorithm *cipher __unused, void *ctx __unused, const void *iv __unused, size_t ivlen __unused)
Definition crypto_null.c:70
void cipher_null_auth(struct cipher_algorithm *cipher __unused, void *ctx __unused, void *auth __unused)
Definition crypto_null.c:89
int cipher_null_setkey(struct cipher_algorithm *cipher __unused, void *ctx __unused, const void *key __unused, size_t keylen __unused)
Definition crypto_null.c:63

Referenced by channel_clear_cipher(), and channel_init().