Fixed comment.
[BearSSL] / inc / bearssl_ssl.h
index 3ff29f6..e91df47 100644 (file)
 #include "bearssl_rand.h"
 #include "bearssl_x509.h"
 
+#ifdef __cplusplus
+extern "C" {
+#endif
+
 /** \file bearssl_ssl.h
  *
  * # SSL
@@ -696,6 +700,110 @@ extern const br_sslrec_out_chapol_class br_sslrec_out_chapol_vtable;
 
 /* ===================================================================== */
 
+/**
+ * \brief Record decryption engine class, for CCM mode.
+ *
+ * This class type extends the decryption engine class with an
+ * initialisation method that receives the parameters needed
+ * for CCM processing: block cipher implementation, block cipher key,
+ * and 4-byte IV.
+ */
+typedef struct br_sslrec_in_ccm_class_ br_sslrec_in_ccm_class;
+struct br_sslrec_in_ccm_class_ {
+       /**
+        * \brief Superclass, as first vtable field.
+        */
+       br_sslrec_in_class inner;
+
+       /**
+        * \brief Engine initialisation method.
+        *
+        * This method sets the vtable field in the context.
+        *
+        * \param ctx           context to initialise.
+        * \param bc_impl       block cipher implementation (CTR+CBC).
+        * \param key           block cipher key.
+        * \param key_len       block cipher key length (in bytes).
+        * \param iv            static IV (4 bytes).
+        * \param tag_len       tag length (in bytes)
+        */
+       void (*init)(const br_sslrec_in_ccm_class **ctx,
+               const br_block_ctrcbc_class *bc_impl,
+               const void *key, size_t key_len,
+               const void *iv, size_t tag_len);
+};
+
+/**
+ * \brief Record encryption engine class, for CCM mode.
+ *
+ * This class type extends the encryption engine class with an
+ * initialisation method that receives the parameters needed
+ * for CCM processing: block cipher implementation, block cipher key,
+ * and 4-byte IV.
+ */
+typedef struct br_sslrec_out_ccm_class_ br_sslrec_out_ccm_class;
+struct br_sslrec_out_ccm_class_ {
+       /**
+        * \brief Superclass, as first vtable field.
+        */
+       br_sslrec_out_class inner;
+
+       /**
+        * \brief Engine initialisation method.
+        *
+        * This method sets the vtable field in the context.
+        *
+        * \param ctx           context to initialise.
+        * \param bc_impl       block cipher implementation (CTR+CBC).
+        * \param key           block cipher key.
+        * \param key_len       block cipher key length (in bytes).
+        * \param iv            static IV (4 bytes).
+        * \param tag_len       tag length (in bytes)
+        */
+       void (*init)(const br_sslrec_out_ccm_class **ctx,
+               const br_block_ctrcbc_class *bc_impl,
+               const void *key, size_t key_len,
+               const void *iv, size_t tag_len);
+};
+
+/**
+ * \brief Context structure for processing records with CCM.
+ *
+ * The same context structure is used for encrypting and decrypting.
+ *
+ * The first field points to the vtable. The other fields are opaque
+ * and shall not be accessed directly.
+ */
+typedef struct {
+       /** \brief Pointer to vtable. */
+       union {
+               const void *gen;
+               const br_sslrec_in_ccm_class *in;
+               const br_sslrec_out_ccm_class *out;
+       } vtable;
+#ifndef BR_DOXYGEN_IGNORE
+       uint64_t seq;
+       union {
+               const br_block_ctrcbc_class *vtable;
+               br_aes_gen_ctrcbc_keys aes;
+       } bc;
+       unsigned char iv[4];
+       size_t tag_len;
+#endif
+} br_sslrec_ccm_context;
+
+/**
+ * \brief Static, constant vtable for record decryption with CCM.
+ */
+extern const br_sslrec_in_ccm_class br_sslrec_in_ccm_vtable;
+
+/**
+ * \brief Static, constant vtable for record encryption with CCM.
+ */
+extern const br_sslrec_out_ccm_class br_sslrec_out_ccm_vtable;
+
+/* ===================================================================== */
+
 /**
  * \brief Type for session parameters, to be saved for session resumption.
  */
@@ -714,9 +822,9 @@ typedef struct {
 
 #ifndef BR_DOXYGEN_IGNORE
 /*
- * Maximum numnber of cipher suites supported by a client or server.
+ * Maximum number of cipher suites supported by a client or server.
  */
-#define BR_MAX_CIPHER_SUITES   40
+#define BR_MAX_CIPHER_SUITES   48
 #endif
 
 /**
@@ -809,6 +917,7 @@ typedef struct {
                br_sslrec_in_cbc_context cbc;
                br_sslrec_gcm_context gcm;
                br_sslrec_chapol_context chapol;
+               br_sslrec_ccm_context ccm;
        } in;
        union {
                const br_sslrec_out_class *vtable;
@@ -816,16 +925,28 @@ typedef struct {
                br_sslrec_out_cbc_context cbc;
                br_sslrec_gcm_context gcm;
                br_sslrec_chapol_context chapol;
+               br_sslrec_ccm_context ccm;
        } out;
 
        /*
-        * The "application data" flag. It is set when application data
-        * can be exchanged, cleared otherwise.
+        * The "application data" flag. Value:
+        *   0   handshake is in process, no application data acceptable
+        *   1   application data can be sent and received
+        *   2   closing, no application data can be sent, but some
+        *       can still be received (and discarded)
         */
        unsigned char application_data;
 
        /*
         * Context RNG.
+        *
+        *   rng_init_done is initially 0. It is set to 1 when the
+        *   basic structure of the RNG is set, and 2 when some
+        *   entropy has been pushed in. The value 2 marks the RNG
+        *   as "properly seeded".
+        *
+        *   rng_os_rand_done is initially 0. It is set to 1 when
+        *   some seeding from the OS or hardware has been attempted.
         */
        br_hmac_drbg_context rng;
        int rng_init_done;
@@ -864,8 +985,8 @@ typedef struct {
        /*
         * Secure renegotiation (RFC 5746): 'reneg' can be:
         *   0   first handshake (server support is not known)
-        *   1   server does not support secure renegotiation
-        *   2   server supports secure renegotiation
+        *   1   peer does not support secure renegotiation
+        *   2   peer supports secure renegotiation
         *
         * The saved_finished buffer contains the client and the
         * server "Finished" values from the last handshake, in
@@ -977,6 +1098,7 @@ typedef struct {
        const br_block_cbcenc_class *iaes_cbcenc;
        const br_block_cbcdec_class *iaes_cbcdec;
        const br_block_ctr_class *iaes_ctr;
+       const br_block_ctrcbc_class *iaes_ctrcbc;
        const br_block_cbcenc_class *ides_cbcenc;
        const br_block_cbcdec_class *ides_cbcdec;
        br_ghash ighash;
@@ -988,6 +1110,8 @@ typedef struct {
        const br_sslrec_out_gcm_class *igcm_out;
        const br_sslrec_in_chapol_class *ichapol_in;
        const br_sslrec_out_chapol_class *ichapol_out;
+       const br_sslrec_in_ccm_class *iccm_in;
+       const br_sslrec_out_ccm_class *iccm_out;
        const br_ec_impl *iec;
        br_rsa_pkcs1_vrfy irsavrfy;
        br_ecdsa_vrfy iecdsa;
@@ -1126,8 +1250,8 @@ static inline void
 br_ssl_engine_set_versions(br_ssl_engine_context *cc,
        unsigned version_min, unsigned version_max)
 {
-       cc->version_min = version_min;
-       cc->version_max = version_max;
+       cc->version_min = (uint16_t)version_min;
+       cc->version_max = (uint16_t)version_max;
 }
 
 /**
@@ -1200,7 +1324,7 @@ br_ssl_engine_set_protocol_names(br_ssl_engine_context *ctx,
        const char **names, size_t num)
 {
        ctx->protocol_names = names;
-       ctx->protocol_names_num = num;
+       ctx->protocol_names_num = (uint16_t)num;
 }
 
 /**
@@ -1263,7 +1387,7 @@ br_ssl_engine_get_hash(br_ssl_engine_context *ctx, int id)
 /**
  * \brief Set the PRF implementation (for TLS 1.0 and 1.1).
  *
- * This function sets (or removes, if `impl` is `NULL`) the implemenation
+ * This function sets (or removes, if `impl` is `NULL`) the implementation
  * for the PRF used in TLS 1.0 and 1.1.
  *
  * \param cc     SSL engine context.
@@ -1278,7 +1402,7 @@ br_ssl_engine_set_prf10(br_ssl_engine_context *cc, br_tls_prf_impl impl)
 /**
  * \brief Set the PRF implementation with SHA-256 (for TLS 1.2).
  *
- * This function sets (or removes, if `impl` is `NULL`) the implemenation
+ * This function sets (or removes, if `impl` is `NULL`) the implementation
  * for the SHA-256 variant of the PRF used in TLS 1.2.
  *
  * \param cc     SSL engine context.
@@ -1293,7 +1417,7 @@ br_ssl_engine_set_prf_sha256(br_ssl_engine_context *cc, br_tls_prf_impl impl)
 /**
  * \brief Set the PRF implementation with SHA-384 (for TLS 1.2).
  *
- * This function sets (or removes, if `impl` is `NULL`) the implemenation
+ * This function sets (or removes, if `impl` is `NULL`) the implementation
  * for the SHA-384 variant of the PRF used in TLS 1.2.
  *
  * \param cc     SSL engine context.
@@ -1321,6 +1445,18 @@ br_ssl_engine_set_aes_cbc(br_ssl_engine_context *cc,
        cc->iaes_cbcdec = impl_dec;
 }
 
+/**
+ * \brief Set the "default" AES/CBC implementations.
+ *
+ * This function configures in the engine the AES implementations that
+ * should provide best runtime performance on the local system, while
+ * still being safe (in particular, constant-time). It also sets the
+ * handlers for CBC records.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_aes_cbc(br_ssl_engine_context *cc);
+
 /**
  * \brief Set the AES/CTR implementation.
  *
@@ -1334,6 +1470,18 @@ br_ssl_engine_set_aes_ctr(br_ssl_engine_context *cc,
        cc->iaes_ctr = impl;
 }
 
+/**
+ * \brief Set the "default" implementations for AES/GCM (AES/CTR + GHASH).
+ *
+ * This function configures in the engine the AES/CTR and GHASH
+ * implementation that should provide best runtime performance on the local
+ * system, while still being safe (in particular, constant-time). It also
+ * sets the handlers for GCM records.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_aes_gcm(br_ssl_engine_context *cc);
+
 /**
  * \brief Set the DES/CBC implementations.
  *
@@ -1350,6 +1498,18 @@ br_ssl_engine_set_des_cbc(br_ssl_engine_context *cc,
        cc->ides_cbcdec = impl_dec;
 }
 
+/**
+ * \brief Set the "default" DES/CBC implementations.
+ *
+ * This function configures in the engine the DES implementations that
+ * should provide best runtime performance on the local system, while
+ * still being safe (in particular, constant-time). It also sets the
+ * handlers for CBC records.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_des_cbc(br_ssl_engine_context *cc);
+
 /**
  * \brief Set the GHASH implementation (used in GCM mode).
  *
@@ -1388,6 +1548,43 @@ br_ssl_engine_set_poly1305(br_ssl_engine_context *cc,
        cc->ipoly = ipoly;
 }
 
+/**
+ * \brief Set the "default" ChaCha20 and Poly1305 implementations.
+ *
+ * This function configures in the engine the ChaCha20 and Poly1305
+ * implementations that should provide best runtime performance on the
+ * local system, while still being safe (in particular, constant-time).
+ * It also sets the handlers for ChaCha20+Poly1305 records.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_chapol(br_ssl_engine_context *cc);
+
+/**
+ * \brief Set the AES/CTR+CBC implementation.
+ *
+ * \param cc     SSL engine context.
+ * \param impl   AES/CTR+CBC encryption/decryption implementation (or `NULL`).
+ */
+static inline void
+br_ssl_engine_set_aes_ctrcbc(br_ssl_engine_context *cc,
+       const br_block_ctrcbc_class *impl)
+{
+       cc->iaes_ctrcbc = impl;
+}
+
+/**
+ * \brief Set the "default" implementations for AES/CCM.
+ *
+ * This function configures in the engine the AES/CTR+CBC
+ * implementation that should provide best runtime performance on the local
+ * system, while still being safe (in particular, constant-time). It also
+ * sets the handlers for CCM records.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_aes_ccm(br_ssl_engine_context *cc);
+
 /**
  * \brief Set the record encryption and decryption engines for CBC + HMAC.
  *
@@ -1420,6 +1617,22 @@ br_ssl_engine_set_gcm(br_ssl_engine_context *cc,
        cc->igcm_out = impl_out;
 }
 
+/**
+ * \brief Set the record encryption and decryption engines for CCM.
+ *
+ * \param cc         SSL engine context.
+ * \param impl_in    record CCM decryption implementation (or `NULL`).
+ * \param impl_out   record CCM encryption implementation (or `NULL`).
+ */
+static inline void
+br_ssl_engine_set_ccm(br_ssl_engine_context *cc,
+       const br_sslrec_in_ccm_class *impl_in,
+       const br_sslrec_out_ccm_class *impl_out)
+{
+       cc->iccm_in = impl_in;
+       cc->iccm_out = impl_out;
+}
+
 /**
  * \brief Set the record encryption and decryption engines for
  * ChaCha20+Poly1305.
@@ -1452,6 +1665,29 @@ br_ssl_engine_set_ec(br_ssl_engine_context *cc, const br_ec_impl *iec)
        cc->iec = iec;
 }
 
+/**
+ * \brief Set the "default" EC implementation.
+ *
+ * This function sets the elliptic curve implementation for ECDH and
+ * ECDHE cipher suites, and for ECDSA support. It selects the fastest
+ * implementation on the current system.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_ec(br_ssl_engine_context *cc);
+
+/**
+ * \brief Get the EC implementation configured in the provided engine.
+ *
+ * \param cc   SSL engine context.
+ * \return  the EC implementation.
+ */
+static inline const br_ec_impl *
+br_ssl_engine_get_ec(br_ssl_engine_context *cc)
+{
+       return cc->iec;
+}
+
 /**
  * \brief Set the RSA signature verification implementation.
  *
@@ -1469,6 +1705,29 @@ br_ssl_engine_set_rsavrfy(br_ssl_engine_context *cc, br_rsa_pkcs1_vrfy irsavrfy)
        cc->irsavrfy = irsavrfy;
 }
 
+/**
+ * \brief Set the "default" RSA implementation (signature verification).
+ *
+ * This function sets the RSA implementation (signature verification)
+ * to the fastest implementation available on the current platform.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_rsavrfy(br_ssl_engine_context *cc);
+
+/**
+ * \brief Get the RSA implementation (signature verification) configured
+ * in the provided engine.
+ *
+ * \param cc   SSL engine context.
+ * \return  the RSA signature verification implementation.
+ */
+static inline br_rsa_pkcs1_vrfy
+br_ssl_engine_get_rsavrfy(br_ssl_engine_context *cc)
+{
+       return cc->irsavrfy;
+}
+
 /*
  * \brief Set the ECDSA implementation (signature verification).
  *
@@ -1490,6 +1749,31 @@ br_ssl_engine_set_ecdsa(br_ssl_engine_context *cc, br_ecdsa_vrfy iecdsa)
        cc->iecdsa = iecdsa;
 }
 
+/**
+ * \brief Set the "default" ECDSA implementation (signature verification).
+ *
+ * This function sets the ECDSA implementation (signature verification)
+ * to the fastest implementation available on the current platform. This
+ * call also sets the elliptic curve implementation itself, there again
+ * to the fastest EC implementation available.
+ *
+ * \param cc   SSL engine context.
+ */
+void br_ssl_engine_set_default_ecdsa(br_ssl_engine_context *cc);
+
+/**
+ * \brief Get the ECDSA implementation (signature verification) configured
+ * in the provided engine.
+ *
+ * \param cc   SSL engine context.
+ * \return  the ECDSA signature verification implementation.
+ */
+static inline br_ecdsa_vrfy
+br_ssl_engine_get_ecdsa(br_ssl_engine_context *cc)
+{
+       return cc->iecdsa;
+}
+
 /**
  * \brief Set the I/O buffer for the SSL engine.
  *
@@ -1657,6 +1941,25 @@ br_ssl_engine_set_session_parameters(br_ssl_engine_context *cc,
        memcpy(&cc->session, pp, sizeof *pp);
 }
 
+/**
+ * \brief Get identifier for the curve used for key exchange.
+ *
+ * If the cipher suite uses ECDHE, then this function returns the
+ * identifier for the curve used for transient parameters. This is
+ * defined during the course of the handshake, when the ServerKeyExchange
+ * is sent (on the server) or received (on the client). If the
+ * cipher suite does not use ECDHE (e.g. static ECDH, or RSA key
+ * exchange), then this value is indeterminate.
+ *
+ * @param cc   SSL engine context.
+ * @return  the ECDHE curve identifier.
+ */
+static inline int
+br_ssl_engine_get_ecdhe_curve(br_ssl_engine_context *cc)
+{
+       return cc->ecdhe_curve;
+}
+
 /**
  * \brief Get the current engine state.
  *
@@ -1763,7 +2066,7 @@ br_ssl_engine_last_error(const br_ssl_engine_context *cc)
  *      Informs the engine that 'len' bytes have been read from the buffer
  *      (extract operation) or written to the buffer (inject operation).
  *      The 'len' value MUST NOT be zero. The 'len' value MUST NOT exceed
- *      that which was obtained from a preceeding br_ssl_engine_xxx_buf()
+ *      that which was obtained from a preceding br_ssl_engine_xxx_buf()
  *      call.
  */
 
@@ -1799,7 +2102,7 @@ void br_ssl_engine_sendapp_ack(br_ssl_engine_context *cc, size_t len);
 /**
  * \brief Get buffer for received application data.
  *
- * If the engine has received application data from the peer, hen this
+ * If the engine has received application data from the peer, then this
  * call returns a pointer to the buffer from where such data shall be
  * read, and its length is written in `*len`. Otherwise, `*len` is set
  * to 0 and `NULL` is returned.
@@ -1918,8 +2221,9 @@ void br_ssl_engine_close(br_ssl_engine_context *cc);
  *
  * If the engine is failed or closed, or if the peer is known not to
  * support secure renegotiation (RFC 5746), or if renegotiations have
- * been disabled with the `BR_OPT_NO_RENEGOTIATION` flag, then this
- * function returns 0 and nothing else happens.
+ * been disabled with the `BR_OPT_NO_RENEGOTIATION` flag, or if there
+ * is buffered incoming application data, then this function returns 0
+ * and nothing else happens.
  *
  * Otherwise, this function returns 1, and a renegotiation attempt is
  * triggered (if a handshake is already ongoing at that point, then
@@ -1930,6 +2234,41 @@ void br_ssl_engine_close(br_ssl_engine_context *cc);
  */
 int br_ssl_engine_renegotiate(br_ssl_engine_context *cc);
 
+/**
+ * \brief Export key material from a connected SSL engine (RFC 5705).
+ *
+ * This calls compute a secret key of arbitrary length from the master
+ * secret of a connected SSL engine. If the provided context is not
+ * currently in "application data" state (initial handshake is not
+ * finished, another handshake is ongoing, or the connection failed or
+ * was closed), then this function returns 0. Otherwise, a secret key of
+ * length `len` bytes is computed and written in the buffer pointed to
+ * by `dst`, and 1 is returned.
+ *
+ * The computed key follows the specification described in RFC 5705.
+ * That RFC includes two key computations, with and without a "context
+ * value". If `context` is `NULL`, then the variant without context is
+ * used; otherwise, the `context_len` bytes located at the address
+ * pointed to by `context` are used in the computation. Note that it
+ * is possible to have a "with context" key with a context length of
+ * zero bytes, by setting `context` to a non-`NULL` value but
+ * `context_len` to 0.
+ *
+ * When context bytes are used, the context length MUST NOT exceed
+ * 65535 bytes.
+ *
+ * \param cc            SSL engine context.
+ * \param dst           destination buffer for exported key.
+ * \param len           exported key length (in bytes).
+ * \param label         disambiguation label.
+ * \param context       context value (or `NULL`).
+ * \param context_len   context length (in bytes).
+ * \return  1 on success, 0 on error.
+ */
+int br_ssl_key_export(br_ssl_engine_context *cc,
+       void *dst, size_t len, const char *label,
+       const void *context, size_t context_len);
+
 /*
  * Pre-declaration for the SSL client context.
  */
@@ -2136,12 +2475,13 @@ struct br_ssl_client_certificate_class_ {
         *     structure was set to -1).
         *
         * In that situation, this callback is invoked to compute the
-        * client-side ECDH: the provided `data` (of length `len` bytes)
+        * client-side ECDH: the provided `data` (of length `*len` bytes)
         * is the server's public key point (as decoded from its
         * certificate), and the client shall multiply that point with
         * its own private key, and write back the X coordinate of the
-        * resulting point in the same buffer, starting at offset 1
-        * (therefore, writing back the complete encoded point works).
+        * resulting point in the same buffer, starting at offset 0.
+        * The `*len` value shall be modified to designate the actual
+        * length of the X coordinate.
         *
         * The callback must uphold the following:
         *
@@ -2158,11 +2498,11 @@ struct br_ssl_client_certificate_class_ {
         *
         * \param pctx   certificate handler context.
         * \param data   server public key point.
-        * \param len    server public key point length (in bytes).
+        * \param len    public key point length / X coordinate length.
         * \return  1 on success, 0 on error.
         */
        uint32_t (*do_keyx)(const br_ssl_client_certificate_class **pctx,
-               unsigned char *data, size_t len);
+               unsigned char *data, size_t *len);
 
        /**
         * \brief Perform a signature (client authentication).
@@ -2327,7 +2667,7 @@ struct br_ssl_client_context_ {
  *     then bit `x` is set (hash function ID is 0 for the special MD5+SHA-1,
  *     or 2 to 6 for the SHA family).
  *
- *   - If ECDSA is suported with hash function of ID `x`, then bit `8+x`
+ *   - If ECDSA is supported with hash function of ID `x`, then bit `8+x`
  *     is set.
  *
  *   - Newer algorithms are symbolic 16-bit identifiers that do not
@@ -2437,6 +2777,17 @@ br_ssl_client_set_rsapub(br_ssl_client_context *cc, br_rsa_public irsapub)
        cc->irsapub = irsapub;
 }
 
+/**
+ * \brief Set the "default" RSA implementation for public-key operations.
+ *
+ * This sets the RSA implementation in the client context (for encrypting
+ * the pre-master secret, in `TLS_RSA_*` cipher suites) to the fastest
+ * available on the current platform.
+ *
+ * \param cc   client context.
+ */
+void br_ssl_client_set_default_rsapub(br_ssl_client_context *cc);
+
 /**
  * \brief Set the minimum ClientHello length (RFC 7685 padding).
  *
@@ -2791,12 +3142,12 @@ struct br_ssl_server_policy_class_ {
         * operation for a key exchange that is not ECDHE. This callback
         * uses the private key.
         *
-        * **For RSA key exchange**, the provided `data` (of length `len`
+        * **For RSA key exchange**, the provided `data` (of length `*len`
         * bytes) shall be decrypted with the server's private key, and
         * the 48-byte premaster secret copied back to the first 48 bytes
         * of `data`.
         *
-        *   - The caller makes sure that `len` is at least 59 bytes.
+        *   - The caller makes sure that `*len` is at least 59 bytes.
         *
         *   - This callback MUST check that the provided length matches
         *     that of the key modulus; it shall report an error otherwise.
@@ -2813,12 +3164,11 @@ struct br_ssl_server_policy_class_ {
         *     in the first 48 bytes of `data` is unimportant (the caller
         *     will use random bytes instead).
         *
-        * **For ECDH key exchange**, the provided `data` (of length `len`
+        * **For ECDH key exchange**, the provided `data` (of length `*len`
         * bytes) is the elliptic curve point from the client. The
         * callback shall multiply it with its private key, and store
-        * the resulting X coordinate in `data`, starting at offset 1
-        * (thus, simply encoding the point in compressed or uncompressed
-        * format in `data` is fine).
+        * the resulting X coordinate in `data`, starting at offset 0,
+        * and set `*len` to the length of the X coordinate.
         *
         *   - If the input array does not have the proper length for
         *     an encoded curve point, then an error (0) shall be reported.
@@ -2837,7 +3187,7 @@ struct br_ssl_server_policy_class_ {
         * \return  1 on success, 0 on error.
         */
        uint32_t (*do_keyx)(const br_ssl_server_policy_class **pctx,
-               unsigned char *data, size_t len);
+               unsigned char *data, size_t *len);
 
        /**
         * \brief Perform a signature (for a ServerKeyExchange message).
@@ -3028,6 +3378,19 @@ typedef struct {
 void br_ssl_session_cache_lru_init(br_ssl_session_cache_lru *cc,
        unsigned char *store, size_t store_len);
 
+/**
+ * \brief Forget an entry in an LRU session cache.
+ *
+ * The session cache context must have been initialised. The entry
+ * with the provided session ID (of exactly 32 bytes) is looked for
+ * in the cache; if located, it is disabled.
+ *
+ * \param cc   session cache context.
+ * \param id   session ID to forget.
+ */
+void br_ssl_session_cache_lru_forget(
+       br_ssl_session_cache_lru *cc, const unsigned char *id);
+
 /**
  * \brief Context structure for a SSL server.
  *
@@ -3146,8 +3509,9 @@ struct br_ssl_server_context_ {
  *      3 = TLS 1.2 with SHA-384
  * -- character 3: encryption
  *      a = AES/CBC
- *      g = AES/GCM
  *      d = 3DES/CBC
+ *      g = AES/GCM
+ *      c = ChaCha20+Poly1305
  */
 
 /**
@@ -3350,7 +3714,7 @@ br_ssl_server_get_client_suites(const br_ssl_server_context *cc, size_t *num)
  *     then bit `x` is set (hash function ID is 0 for the special MD5+SHA-1,
  *     or 2 to 6 for the SHA family).
  *
- *   - If ECDSA is suported with hash function of ID `x`, then bit `8+x`
+ *   - If ECDSA is supported with hash function of ID `x`, then bit `8+x`
  *     is set.
  *
  *   - Newer algorithms are symbolic 16-bit identifiers that do not
@@ -3876,6 +4240,16 @@ int br_sslio_close(br_sslio_context *cc);
 #define BR_TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256      0xC031
 #define BR_TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384      0xC032
 
+/* From RFC 6655 and 7251 */
+#define BR_TLS_RSA_WITH_AES_128_CCM                  0xC09C
+#define BR_TLS_RSA_WITH_AES_256_CCM                  0xC09D
+#define BR_TLS_RSA_WITH_AES_128_CCM_8                0xC0A0
+#define BR_TLS_RSA_WITH_AES_256_CCM_8                0xC0A1
+#define BR_TLS_ECDHE_ECDSA_WITH_AES_128_CCM          0xC0AC
+#define BR_TLS_ECDHE_ECDSA_WITH_AES_256_CCM          0xC0AD
+#define BR_TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8        0xC0AE
+#define BR_TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8        0xC0AF
+
 /* From RFC 7905 */
 #define BR_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256     0xCCA8
 #define BR_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256   0xCCA9
@@ -3915,4 +4289,8 @@ int br_sslio_close(br_sslio_context *cc);
 #define BR_ALERT_UNSUPPORTED_EXTENSION     110
 #define BR_ALERT_NO_APPLICATION_PROTOCOL   120
 
+#ifdef __cplusplus
+}
+#endif
+
 #endif