LCOV - code coverage report
Current view: top level - builds/gnutls/coverage/gnutls-git/lib - cert-cred.c (source / functions) Hit Total Coverage
Test: GnuTLS-3.6.14 Code Coverage Lines: 281 379 74.1 %
Date: 2020-10-30 04:50:48 Functions: 21 26 80.8 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :  * Copyright (C) 2001-2016 Free Software Foundation, Inc.
       3             :  * Copyright (C) 2015-2017 Red Hat, Inc.
       4             :  *
       5             :  * Author: Nikos Mavrogiannopoulos
       6             :  *
       7             :  * This file is part of GnuTLS.
       8             :  *
       9             :  * The GnuTLS is free software; you can redistribute it and/or
      10             :  * modify it under the terms of the GNU Lesser General Public License
      11             :  * as published by the Free Software Foundation; either version 2.1 of
      12             :  * the License, or (at your option) any later version.
      13             :  *
      14             :  * This library is distributed in the hope that it will be useful, but
      15             :  * WITHOUT ANY WARRANTY; without even the implied warranty of
      16             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      17             :  * Lesser General Public License for more details.
      18             :  *
      19             :  * You should have received a copy of the GNU Lesser General Public License
      20             :  * along with this program.  If not, see <https://www.gnu.org/licenses/>
      21             :  *
      22             :  */
      23             : 
      24             : /* Some of the stuff needed for Certificate authentication is contained
      25             :  * in this file.
      26             :  */
      27             : 
      28             : #include "gnutls_int.h"
      29             : #include "errors.h"
      30             : #include <auth/cert.h>
      31             : #include <datum.h>
      32             : #include <mpi.h>
      33             : #include <global.h>
      34             : #include <algorithms.h>
      35             : #include <dh.h>
      36             : #include "str.h"
      37             : #include <state.h>
      38             : #include <auth.h>
      39             : #include <x509.h>
      40             : #include <str_array.h>
      41             : #include <x509/verify-high.h>
      42             : #include "x509/x509_int.h"
      43             : #include "x509/common.h"
      44             : #include "dh.h"
      45             : #include "cert-cred.h"
      46             : 
      47             : 
      48             : /*
      49             :  * Adds a public/private key pair to a certificate credential
      50             :  */
      51             : int
      52       11343 : _gnutls_certificate_credential_append_keypair(gnutls_certificate_credentials_t res,
      53             :                                        gnutls_privkey_t key,
      54             :                                        gnutls_str_array_t names,
      55             :                                        gnutls_pcert_st * crt,
      56             :                                        int nr)
      57             : {
      58       22686 :         res->sorted_cert_idx = gnutls_realloc_fast(res->sorted_cert_idx,
      59       11343 :                                                 (1 + res->ncerts) *
      60             :                                                 sizeof(unsigned int));
      61       11343 :         if (res->sorted_cert_idx == NULL)
      62           0 :                 return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
      63             : 
      64       22686 :         res->certs = gnutls_realloc_fast(res->certs,
      65       11343 :                                          (1 + res->ncerts) *
      66             :                                          sizeof(certs_st));
      67       11343 :         if (res->certs == NULL)
      68           0 :                 return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
      69             : 
      70       11343 :         memset(&res->certs[res->ncerts], 0, sizeof(res->certs[0]));
      71             : 
      72       11343 :         res->certs[res->ncerts].cert_list = crt;
      73       11343 :         res->certs[res->ncerts].cert_list_length = nr;
      74       11343 :         res->certs[res->ncerts].names = names;
      75       11343 :         res->certs[res->ncerts].pkey = key;
      76             : 
      77       11343 :         if (_gnutls13_sign_get_compatible_with_privkey(key))
      78       11278 :                 res->tls13_ok = 1;
      79             : 
      80             :         /* move RSA-PSS certificates before any RSA key.
      81             :          * Note that we cannot assume that any previous pointers
      82             :          * to sorted list are ok, due to the realloc in res->certs. */
      83       11343 :         if (crt->pubkey->params.algo == GNUTLS_PK_RSA_PSS) {
      84             :                 unsigned i,ridx;
      85             :                 unsigned tmp;
      86             : 
      87          45 :                 for (i=0;i<res->ncerts;i++) {
      88           7 :                         ridx = res->sorted_cert_idx[i];
      89             : 
      90           7 :                         if (res->certs[ridx].cert_list->pubkey->params.algo == GNUTLS_PK_RSA) {
      91           7 :                                 tmp = ridx;
      92           7 :                                 res->sorted_cert_idx[i] = res->ncerts;
      93           7 :                                 res->sorted_cert_idx[res->ncerts] = tmp;
      94           7 :                                 goto finish;
      95             :                         }
      96             :                 }
      97             :         }
      98             : 
      99             :         /* otherwise append it normally on the end */
     100       11336 :         res->sorted_cert_idx[res->ncerts] = res->ncerts;
     101             : 
     102             :  finish:
     103             :         return 0;
     104             : 
     105             : }
     106             : 
     107             : 
     108             : /**
     109             :  * gnutls_certificate_set_key:
     110             :  * @res: is a #gnutls_certificate_credentials_t type.
     111             :  * @names: is an array of DNS names belonging to the public-key (NULL if none)
     112             :  * @names_size: holds the size of the names list
     113             :  * @pcert_list: contains a certificate list (chain) or raw public-key
     114             :  * @pcert_list_size: holds the size of the certificate list
     115             :  * @key: is a #gnutls_privkey_t key corresponding to the first public-key in pcert_list
     116             :  *
     117             :  * This function sets a public/private key pair in the
     118             :  * gnutls_certificate_credentials_t type. The given public key may be encapsulated
     119             :  * in a certificate or can be given as a raw key. This function may be
     120             :  * called more than once, in case multiple key pairs exist for
     121             :  * the server. For clients that want to send more than their own end-
     122             :  * entity certificate (e.g., also an intermediate CA cert), the full
     123             :  * certificate chain must be provided in @pcert_list.
     124             :  *
     125             :  * Note that the @key will become part of the credentials structure and must
     126             :  * not be deallocated. It will be automatically deallocated when the @res structure
     127             :  * is deinitialized.
     128             :  *
     129             :  * If this function fails, the @res structure is at an undefined state and it must
     130             :  * not be reused to load other keys or certificates.
     131             :  *
     132             :  * Note that, this function by default returns zero on success and a negative value on error.
     133             :  * Since 3.5.6, when the flag %GNUTLS_CERTIFICATE_API_V2 is set using gnutls_certificate_set_flags()
     134             :  * it returns an index (greater or equal to zero). That index can be used for other functions to refer to the added key-pair.
     135             :  *
     136             :  * Since GnuTLS 3.6.6 this function also handles raw public keys.
     137             :  *
     138             :  * Returns: On success this functions returns zero, and otherwise a negative value on error (see above for modifying that behavior).
     139             :  *
     140             :  * Since: 3.0
     141             :  **/
     142             : int
     143          63 : gnutls_certificate_set_key(gnutls_certificate_credentials_t res,
     144             :                            const char **names,
     145             :                            int names_size,
     146             :                            gnutls_pcert_st * pcert_list,
     147             :                            int pcert_list_size,
     148             :                            gnutls_privkey_t key)
     149             : {
     150          63 :         int ret, i;
     151          63 :         gnutls_str_array_t str_names;
     152          63 :         gnutls_pcert_st *new_pcert_list;
     153             : 
     154             :         /* Sanity checks */
     155             :         // Check for a valid credential struct
     156          63 :         if (res == NULL) {
     157           0 :                 return gnutls_assert_val(GNUTLS_E_ILLEGAL_PARAMETER);
     158             :         }
     159             : 
     160             :         // A complete key pair must be given
     161          63 :         if (pcert_list == NULL || key == NULL) {
     162           0 :                 return gnutls_assert_val(GNUTLS_E_INSUFFICIENT_CREDENTIALS);
     163             :         }
     164             : 
     165             :         /* Process the names, if any */
     166          63 :         _gnutls_str_array_init(&str_names);
     167             : 
     168          63 :         if (names != NULL && names_size > 0) {
     169          54 :                 for (i = 0; i < names_size; i++) {
     170          36 :                         ret =
     171          72 :                             _gnutls_str_array_append_idna(&str_names, names[i],
     172          36 :                                                      strlen(names[i]));
     173          36 :                         if (ret < 0) {
     174           0 :                                 ret = gnutls_assert_val(ret);
     175           0 :                                 goto cleanup;
     176             :                         }
     177             :                 }
     178          45 :         } else if (names == NULL && pcert_list[0].type == GNUTLS_CRT_X509) {
     179          45 :                 gnutls_x509_crt_t crt;
     180             : 
     181          45 :                 ret = gnutls_x509_crt_init(&crt);
     182          45 :                 if (ret < 0) {
     183           0 :                         gnutls_assert();
     184           0 :                         goto cleanup;
     185             :                 }
     186             : 
     187          45 :                 ret = gnutls_x509_crt_import(crt, &pcert_list[0].cert, GNUTLS_X509_FMT_DER);
     188          45 :                 if (ret < 0) {
     189           0 :                         gnutls_assert();
     190           0 :                         gnutls_x509_crt_deinit(crt);
     191           0 :                         goto cleanup;
     192             :                 }
     193             : 
     194          45 :                 ret = _gnutls_get_x509_name(crt, &str_names);
     195          45 :                 gnutls_x509_crt_deinit(crt);
     196             : 
     197          45 :                 if (ret < 0) {
     198           0 :                         gnutls_assert();
     199           0 :                         goto cleanup;
     200             :                 }
     201             :         }
     202             : 
     203          63 :         if (res->pin.cb)
     204           0 :                 gnutls_privkey_set_pin_function(key, res->pin.cb,
     205             :                                                 res->pin.data);
     206             : 
     207          63 :         new_pcert_list = gnutls_malloc(sizeof(gnutls_pcert_st) * pcert_list_size);
     208          63 :         if (new_pcert_list == NULL) {
     209           0 :                 return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
     210             :         }
     211          63 :         memcpy(new_pcert_list, pcert_list, sizeof(gnutls_pcert_st) * pcert_list_size);
     212             : 
     213          63 :         ret =
     214          63 :             _gnutls_certificate_credential_append_keypair(res, key, str_names,
     215             :                                                    new_pcert_list,
     216             :                                                    pcert_list_size);
     217          63 :         if (ret < 0) {
     218           0 :                 gnutls_assert();
     219           0 :                 gnutls_free(new_pcert_list);
     220           0 :                 goto cleanup;
     221             :         }
     222             : 
     223          63 :         res->ncerts++;
     224             : 
     225             :         /* Unlike gnutls_certificate_set_x509_key, we deinitialize everything
     226             :          * local after a failure. That is because the caller is responsible for
     227             :          * freeing these values after a failure, and if we keep references we
     228             :          * lead to double freeing */
     229          63 :         if ((ret = _gnutls_check_key_cert_match(res)) < 0) {
     230           1 :                 gnutls_assert();
     231           1 :                 gnutls_free(new_pcert_list);
     232           1 :                 res->ncerts--;
     233           1 :                 goto cleanup;
     234             :         }
     235             : 
     236          62 :         CRED_RET_SUCCESS(res);
     237             : 
     238           1 :       cleanup:
     239           1 :         _gnutls_str_array_clear(&str_names);
     240             :         return ret;
     241             : }
     242             : 
     243             : /**
     244             :  * gnutls_certificate_free_keys:
     245             :  * @sc: is a #gnutls_certificate_credentials_t type.
     246             :  *
     247             :  * This function will delete all the keys and the certificates associated
     248             :  * with the given credentials. This function must not be called when a
     249             :  * TLS negotiation that uses the credentials is in progress.
     250             :  *
     251             :  **/
     252        6922 : void gnutls_certificate_free_keys(gnutls_certificate_credentials_t sc)
     253             : {
     254        6922 :         unsigned i, j;
     255             : 
     256       17884 :         for (i = 0; i < sc->ncerts; i++) {
     257       23014 :                 for (j = 0; j < sc->certs[i].cert_list_length; j++) {
     258       12052 :                         gnutls_pcert_deinit(&sc->certs[i].cert_list[j]);
     259             :                 }
     260       10962 :                 gnutls_free(sc->certs[i].cert_list);
     261             : 
     262       10979 :                 for (j = 0; j < sc->certs[i].ocsp_data_length; j++) {
     263          17 :                         gnutls_free(sc->certs[i].ocsp_data[j].response.data);
     264             :                 }
     265       10962 :                 _gnutls_str_array_clear(&sc->certs[i].names);
     266       10962 :                 gnutls_privkey_deinit(sc->certs[i].pkey);
     267             :         }
     268             : 
     269        6922 :         gnutls_free(sc->certs);
     270        6922 :         gnutls_free(sc->sorted_cert_idx);
     271             : 
     272        6922 :         sc->ncerts = 0;
     273        6922 : }
     274             : 
     275             : /**
     276             :  * gnutls_certificate_free_cas:
     277             :  * @sc: is a #gnutls_certificate_credentials_t type.
     278             :  *
     279             :  * This function was operational on very early versions of gnutls.
     280             :  * Due to internal refactorings and the fact that this was hardly ever
     281             :  * used, it is currently a no-op.
     282             :  *
     283             :  **/
     284           0 : void gnutls_certificate_free_cas(gnutls_certificate_credentials_t sc)
     285             : {
     286           0 :         return;
     287             : }
     288             : 
     289             : /**
     290             :  * gnutls_certificate_get_issuer:
     291             :  * @sc: is a #gnutls_certificate_credentials_t type.
     292             :  * @cert: is the certificate to find issuer for
     293             :  * @issuer: Will hold the issuer if any. Should be treated as constant.
     294             :  * @flags: Use zero or %GNUTLS_TL_GET_COPY
     295             :  *
     296             :  * This function will return the issuer of a given certificate.
     297             :  * If the flag %GNUTLS_TL_GET_COPY is specified a copy of the issuer
     298             :  * will be returned which must be freed using gnutls_x509_crt_deinit().
     299             :  * In that case the provided @issuer must not be initialized.
     300             :  *
     301             :  * As with gnutls_x509_trust_list_get_issuer() this function requires
     302             :  * the %GNUTLS_TL_GET_COPY flag in order to operate with PKCS#11 trust
     303             :  * lists in a thread-safe way.
     304             :  *
     305             :  * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise a
     306             :  *   negative error value.
     307             :  *
     308             :  * Since: 3.0
     309             :  **/
     310             : int
     311           5 : gnutls_certificate_get_issuer(gnutls_certificate_credentials_t sc,
     312             :                               gnutls_x509_crt_t cert,
     313             :                               gnutls_x509_crt_t * issuer,
     314             :                               unsigned int flags)
     315             : {
     316           5 :         return gnutls_x509_trust_list_get_issuer(sc->tlist, cert, issuer,
     317             :                                                  flags);
     318             : }
     319             : 
     320             : /**
     321             :  * gnutls_certificate_get_crt_raw:
     322             :  * @sc: is a #gnutls_certificate_credentials_t type.
     323             :  * @idx1: the index of the certificate chain if multiple are present
     324             :  * @idx2: the index of the certificate in the chain. Zero gives the server's certificate.
     325             :  * @cert: Will hold the DER encoded certificate.
     326             :  *
     327             :  * This function will return the DER encoded certificate of the
     328             :  * server or any other certificate on its certificate chain (based on @idx2).
     329             :  * The returned data should be treated as constant and only accessible during the lifetime
     330             :  * of @sc. The @idx1 matches the value gnutls_certificate_set_x509_key() and friends
     331             :  * functions.
     332             :  *
     333             :  * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise a
     334             :  *   negative error value. In case the indexes are out of bounds %GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE
     335             :  *   is returned.
     336             :  *
     337             :  * Since: 3.2.5
     338             :  **/
     339             : int
     340          64 : gnutls_certificate_get_crt_raw(gnutls_certificate_credentials_t sc,
     341             :                                unsigned idx1,
     342             :                                unsigned idx2, gnutls_datum_t * cert)
     343             : {
     344          64 :         if (idx1 >= sc->ncerts)
     345           0 :                 return
     346           0 :                     gnutls_assert_val
     347             :                     (GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE);
     348             : 
     349          64 :         if (idx2 >= sc->certs[idx1].cert_list_length)
     350           0 :                 return
     351           0 :                     gnutls_assert_val
     352             :                     (GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE);
     353             : 
     354          64 :         cert->data = sc->certs[idx1].cert_list[idx2].cert.data;
     355          64 :         cert->size = sc->certs[idx1].cert_list[idx2].cert.size;
     356             : 
     357          64 :         return 0;
     358             : }
     359             : 
     360             : /**
     361             :  * gnutls_certificate_free_ca_names:
     362             :  * @sc: is a #gnutls_certificate_credentials_t type.
     363             :  *
     364             :  * This function will delete all the CA name in the given
     365             :  * credentials. Clients may call this to save some memory since in
     366             :  * client side the CA names are not used. Servers might want to use
     367             :  * this function if a large list of trusted CAs is present and
     368             :  * sending the names of it would just consume bandwidth without providing
     369             :  * information to client.
     370             :  *
     371             :  * CA names are used by servers to advertise the CAs they support to
     372             :  * clients.
     373             :  **/
     374           0 : void gnutls_certificate_free_ca_names(gnutls_certificate_credentials_t sc)
     375             : {
     376           0 :         _gnutls_free_datum(&sc->tlist->x509_rdn_sequence);
     377           0 : }
     378             : 
     379             : 
     380             : /**
     381             :  * gnutls_certificate_free_credentials:
     382             :  * @sc: is a #gnutls_certificate_credentials_t type.
     383             :  *
     384             :  * Free a gnutls_certificate_credentials_t structure.
     385             :  *
     386             :  * This function does not free any temporary parameters associated
     387             :  * with this structure (ie RSA and DH parameters are not freed by this
     388             :  * function).
     389             :  **/
     390             : void
     391        6922 : gnutls_certificate_free_credentials(gnutls_certificate_credentials_t sc)
     392             : {
     393             :         // Check for valid pointer and otherwise do nothing
     394        6922 :         if (sc == NULL)
     395             :                 return;
     396             : 
     397        6922 :         gnutls_x509_trust_list_deinit(sc->tlist, 1);
     398        6922 :         gnutls_certificate_free_keys(sc);
     399        6922 :         memset(sc->pin_tmp, 0, sizeof(sc->pin_tmp));
     400             : 
     401        6922 :         if (sc->deinit_dh_params) {
     402           0 :                 gnutls_dh_params_deinit(sc->dh_params);
     403             :         }
     404             : 
     405        6922 :         gnutls_free(sc);
     406             : }
     407             : 
     408             : 
     409             : /**
     410             :  * gnutls_certificate_allocate_credentials:
     411             :  * @res: is a pointer to a #gnutls_certificate_credentials_t type.
     412             :  *
     413             :  * Allocate a gnutls_certificate_credentials_t structure.
     414             :  *
     415             :  * Returns: %GNUTLS_E_SUCCESS on success, or an error code.
     416             :  **/
     417             : int
     418        7332 : gnutls_certificate_allocate_credentials(gnutls_certificate_credentials_t *
     419             :                                         res)
     420             : {
     421        7332 :         int ret;
     422             : 
     423        7332 :         *res = gnutls_calloc(1, sizeof(certificate_credentials_st));
     424             : 
     425        7332 :         if (*res == NULL)
     426             :                 return GNUTLS_E_MEMORY_ERROR;
     427             : 
     428        7332 :         ret = gnutls_x509_trust_list_init(&(*res)->tlist, 0);
     429        7332 :         if (ret < 0) {
     430           0 :                 gnutls_assert();
     431           0 :                 gnutls_free(*res);
     432           0 :                 return GNUTLS_E_MEMORY_ERROR;
     433             :         }
     434        7332 :         (*res)->verify_bits = DEFAULT_MAX_VERIFY_BITS;
     435        7332 :         (*res)->verify_depth = DEFAULT_MAX_VERIFY_DEPTH;
     436             : 
     437             : 
     438        7332 :         return 0;
     439             : }
     440             : 
     441             : /* converts the given x509 certificate list to gnutls_pcert_st* and allocates
     442             :  * space for them.
     443             :  */
     444           8 : static gnutls_pcert_st *alloc_and_load_x509_certs(gnutls_x509_crt_t *
     445             :                                                   certs, unsigned ncerts)
     446             : {
     447           8 :         gnutls_pcert_st *local_certs;
     448           8 :         int ret = 0;
     449           8 :         unsigned i, j;
     450             : 
     451           8 :         if (certs == NULL)
     452             :                 return NULL;
     453             : 
     454           8 :         local_certs = gnutls_malloc(sizeof(gnutls_pcert_st) * ncerts);
     455           8 :         if (local_certs == NULL) {
     456           0 :                 gnutls_assert();
     457           0 :                 return NULL;
     458             :         }
     459             : 
     460          24 :         for (i = 0; i < ncerts; i++) {
     461          16 :                 ret = gnutls_pcert_import_x509(&local_certs[i], certs[i], 0);
     462          16 :                 if (ret < 0)
     463             :                         break;
     464             :         }
     465             : 
     466           8 :         if (ret < 0) {
     467           0 :                 gnutls_assert();
     468           0 :                 for (j = 0; j < i; j++) {
     469           0 :                         gnutls_pcert_deinit(&local_certs[j]);
     470             :                 }
     471           0 :                 gnutls_free(local_certs);
     472           0 :                 return NULL;
     473             :         }
     474             : 
     475             :         return local_certs;
     476             : }
     477             : 
     478             : /* converts the given x509 key to gnutls_privkey* and allocates
     479             :  * space for it.
     480             :  */
     481             : static gnutls_privkey_t
     482           8 : alloc_and_load_x509_key(gnutls_x509_privkey_t key, int deinit)
     483             : {
     484           8 :         gnutls_privkey_t local_key;
     485           8 :         int ret = 0;
     486             : 
     487           8 :         if (key == NULL)
     488             :                 return NULL;
     489             : 
     490           8 :         ret = gnutls_privkey_init(&local_key);
     491           8 :         if (ret < 0) {
     492           0 :                 gnutls_assert();
     493           0 :                 return NULL;
     494             :         }
     495             : 
     496           8 :         ret =
     497           8 :             gnutls_privkey_import_x509(local_key, key,
     498             :                                        deinit ?
     499             :                                        GNUTLS_PRIVKEY_IMPORT_AUTO_RELEASE : 0);
     500           8 :         if (ret < 0) {
     501           0 :                 gnutls_assert();
     502           0 :                 gnutls_privkey_deinit(local_key);
     503           0 :                 return NULL;
     504             :         }
     505             : 
     506           8 :         return local_key;
     507             : }
     508             : 
     509             : #ifdef ENABLE_PKCS11
     510             : 
     511             : /* converts the given raw key to gnutls_privkey* and allocates
     512             :  * space for it.
     513             :  */
     514             : static gnutls_privkey_t
     515           0 : alloc_and_load_pkcs11_key(gnutls_pkcs11_privkey_t key, int deinit)
     516             : {
     517           0 :         gnutls_privkey_t local_key;
     518           0 :         int ret = 0;
     519             : 
     520           0 :         if (key == NULL)
     521             :                 return NULL;
     522             : 
     523           0 :         ret = gnutls_privkey_init(&local_key);
     524           0 :         if (ret < 0) {
     525           0 :                 gnutls_assert();
     526           0 :                 return NULL;
     527             :         }
     528             : 
     529           0 :         ret =
     530           0 :             gnutls_privkey_import_pkcs11(local_key, key,
     531             :                                          deinit ?
     532             :                                          GNUTLS_PRIVKEY_IMPORT_AUTO_RELEASE
     533             :                                          : 0);
     534           0 :         if (ret < 0) {
     535           0 :                 gnutls_assert();
     536           0 :                 gnutls_privkey_deinit(local_key);
     537           0 :                 return NULL;
     538             :         }
     539             : 
     540           0 :         return local_key;
     541             : }
     542             : 
     543             : #endif
     544             : 
     545             : /**
     546             :  * gnutls_certificate_server_set_request:
     547             :  * @session: is a #gnutls_session_t type.
     548             :  * @req: is one of GNUTLS_CERT_REQUEST, GNUTLS_CERT_REQUIRE, GNUTLS_CERT_IGNORE
     549             :  *
     550             :  * This function specifies if we (in case of a server) are going to
     551             :  * send a certificate request message to the client. If @req is
     552             :  * GNUTLS_CERT_REQUIRE then the server will return the %GNUTLS_E_NO_CERTIFICATE_FOUND
     553             :  * error if the peer does not provide a certificate. If you do not call this
     554             :  * function then the client will not be asked to send a certificate. Invoking
     555             :  * the function with @req GNUTLS_CERT_IGNORE has the same effect.
     556             :  **/
     557             : void
     558       10446 : gnutls_certificate_server_set_request(gnutls_session_t session,
     559             :                                       gnutls_certificate_request_t req)
     560             : {
     561       10446 :         session->internals.send_cert_req = req;
     562       10446 : }
     563             : 
     564           9 : static int call_legacy_cert_cb1(gnutls_session_t session,
     565             :                                 const struct gnutls_cert_retr_st *info,
     566             :                                 gnutls_pcert_st **certs,
     567             :                                 unsigned int *pcert_length,
     568             :                                 gnutls_ocsp_data_st **ocsp,
     569             :                                 unsigned int *ocsp_length,
     570             :                                 gnutls_privkey_t *privkey,
     571             :                                 unsigned int *flags)
     572             : {
     573           9 :         gnutls_retr2_st st2;
     574           9 :         gnutls_pcert_st *local_certs = NULL;
     575           9 :         gnutls_privkey_t local_key = NULL;
     576           9 :         unsigned i;
     577           9 :         int ret;
     578             : 
     579           9 :         *ocsp_length = 0;
     580             : 
     581           9 :         memset(&st2, 0, sizeof(st2));
     582             : 
     583          18 :         ret = info->cred->legacy_cert_cb1(session, info->req_ca_rdn, info->nreqs,
     584           9 :                                           info->pk_algos, info->pk_algos_length,
     585             :                                           &st2);
     586           9 :         if (ret < 0)
     587           0 :                 return gnutls_assert_val(ret);
     588             : 
     589           9 :         if (st2.ncerts == 0) {
     590           1 :                 *pcert_length = 0;
     591           1 :                 *ocsp_length = 0;
     592           1 :                 *privkey = NULL;
     593           1 :                 return 0;
     594             :         }
     595             : 
     596           8 :         if (st2.cert_type != GNUTLS_CRT_X509) {
     597           0 :                 gnutls_assert();
     598           0 :                 ret = GNUTLS_E_INVALID_REQUEST;
     599           0 :                 goto cleanup;
     600             :         }
     601             : 
     602           8 :         local_certs =
     603           8 :             alloc_and_load_x509_certs(st2.cert.x509, st2.ncerts);
     604           8 :         if (local_certs == NULL) {
     605           0 :                 gnutls_assert();
     606           0 :                 ret = GNUTLS_E_MEMORY_ERROR;
     607           0 :                 goto cleanup;
     608             :         }
     609             : 
     610           8 :         switch (st2.key_type) {
     611             : #ifdef ENABLE_PKCS11
     612           0 :         case GNUTLS_PRIVKEY_PKCS11:
     613           0 :                 if (st2.key.pkcs11 != NULL) {
     614           0 :                         local_key =
     615           0 :                             alloc_and_load_pkcs11_key(st2.key.pkcs11,
     616           0 :                                                       st2.deinit_all);
     617           0 :                         if (local_key == NULL) {
     618           0 :                                 gnutls_assert();
     619           0 :                                 ret = GNUTLS_E_INTERNAL_ERROR;
     620           0 :                                 goto cleanup;
     621             :                         }
     622             :                 }
     623             :                 break;
     624             : #endif
     625           8 :         case GNUTLS_PRIVKEY_X509:
     626           8 :                 if (st2.key.x509 != NULL) {
     627           8 :                         local_key =
     628          16 :                             alloc_and_load_x509_key(st2.key.x509,
     629           8 :                                                     st2.deinit_all);
     630           8 :                         if (local_key == NULL) {
     631           0 :                                 gnutls_assert();
     632           0 :                                 ret = GNUTLS_E_INTERNAL_ERROR;
     633           0 :                                 goto cleanup;
     634             :                         }
     635             :                 }
     636             :                 break;
     637           0 :         default:
     638           0 :                 gnutls_assert();
     639           0 :                 ret = GNUTLS_E_INVALID_REQUEST;
     640           0 :                 goto cleanup;
     641             :         }
     642             : 
     643           8 :         *privkey = local_key;
     644           8 :         *certs = local_certs;
     645           8 :         *pcert_length = st2.ncerts;
     646             : 
     647             :         /* flag the caller to deinitialize our values */
     648           8 :         *flags |= GNUTLS_CERT_RETR_DEINIT_ALL;
     649             : 
     650           8 :         ret = 0;
     651             : 
     652           8 :  cleanup:
     653             : 
     654           8 :         if (st2.cert_type == GNUTLS_CRT_X509) {
     655           8 :                 if (st2.deinit_all) {
     656          24 :                         for (i = 0; i < st2.ncerts; i++) {
     657          16 :                                 gnutls_x509_crt_deinit(st2.cert.x509[i]);
     658             :                         }
     659           8 :                         gnutls_free(st2.cert.x509);
     660             :                 }
     661             :         }
     662             : 
     663             :         return ret;
     664             : 
     665             : }
     666             : 
     667             : /**
     668             :  * gnutls_certificate_set_retrieve_function:
     669             :  * @cred: is a #gnutls_certificate_credentials_t type.
     670             :  * @func: is the callback function
     671             :  *
     672             :  * This function sets a callback to be called in order to retrieve the
     673             :  * certificate to be used in the handshake. The callback will take control
     674             :  * only if a certificate is requested by the peer. You are advised
     675             :  * to use gnutls_certificate_set_retrieve_function2() because it
     676             :  * is much more efficient in the processing it requires from gnutls.
     677             :  *
     678             :  * The callback's function prototype is:
     679             :  * int (*callback)(gnutls_session_t, const gnutls_datum_t* req_ca_dn, int nreqs,
     680             :  * const gnutls_pk_algorithm_t* pk_algos, int pk_algos_length, gnutls_retr2_st* st);
     681             :  *
     682             :  * @req_ca_dn is only used in X.509 certificates.
     683             :  * Contains a list with the CA names that the server considers trusted.
     684             :  * This is a hint and typically the client should send a certificate that is signed
     685             :  * by one of these CAs. These names, when available, are DER encoded. To get a more
     686             :  * meaningful value use the function gnutls_x509_rdn_get().
     687             :  *
     688             :  * @pk_algos contains a list with server's acceptable public key algorithms.
     689             :  * The certificate returned should support the server's given algorithms.
     690             :  *
     691             :  * @st should contain the certificates and private keys.
     692             :  *
     693             :  * If the callback function is provided then gnutls will call it, in the
     694             :  * handshake, after the certificate request message has been received.
     695             :  *
     696             :  * In server side pk_algos and req_ca_dn are NULL.
     697             :  *
     698             :  * The callback function should set the certificate list to be sent,
     699             :  * and return 0 on success. If no certificate was selected then the
     700             :  * number of certificates should be set to zero. The value (-1)
     701             :  * indicates error and the handshake will be terminated. If both certificates
     702             :  * are set in the credentials and a callback is available, the callback
     703             :  * takes predence.
     704             :  *
     705             :  * Since: 3.0
     706             :  **/
     707          11 : void gnutls_certificate_set_retrieve_function
     708             :     (gnutls_certificate_credentials_t cred,
     709             :      gnutls_certificate_retrieve_function * func)
     710             : {
     711          11 :         cred->legacy_cert_cb1 = func;
     712          11 :         if (!func)
     713           1 :                 cred->get_cert_callback3 = NULL;
     714             :         else
     715          10 :                 cred->get_cert_callback3 = call_legacy_cert_cb1;
     716          11 : }
     717             : 
     718         219 : static int call_legacy_cert_cb2(gnutls_session_t session,
     719             :                                 const struct gnutls_cert_retr_st *info,
     720             :                                 gnutls_pcert_st **certs,
     721             :                                 unsigned int *pcert_length,
     722             :                                 gnutls_ocsp_data_st **ocsp,
     723             :                                 unsigned int *ocsp_length,
     724             :                                 gnutls_privkey_t *privkey,
     725             :                                 unsigned int *flags)
     726             : {
     727         219 :         int ret;
     728         219 :         *ocsp_length = 0;
     729             :         /* flags will be assumed to be zero */
     730             : 
     731         438 :         ret = info->cred->legacy_cert_cb2(session, info->req_ca_rdn, info->nreqs,
     732         219 :                                           info->pk_algos, info->pk_algos_length,
     733             :                                           certs, pcert_length, privkey);
     734         219 :         if (ret < 0) {
     735           0 :                 gnutls_assert();
     736             :         }
     737         219 :         return ret;
     738             : }
     739             : 
     740             : /**
     741             :  * gnutls_certificate_set_retrieve_function2:
     742             :  * @cred: is a #gnutls_certificate_credentials_t type.
     743             :  * @func: is the callback function
     744             :  *
     745             :  * This function sets a callback to be called in order to retrieve the
     746             :  * certificate to be used in the handshake. The callback will take control
     747             :  * only if a certificate is requested by the peer.
     748             :  *
     749             :  * The callback's function prototype is:
     750             :  * int (*callback)(gnutls_session_t, const gnutls_datum_t* req_ca_dn, int nreqs,
     751             :  * const gnutls_pk_algorithm_t* pk_algos, int pk_algos_length, gnutls_pcert_st** pcert,
     752             :  * unsigned int *pcert_length, gnutls_privkey_t * pkey);
     753             :  *
     754             :  * @req_ca_dn is only used in X.509 certificates.
     755             :  * Contains a list with the CA names that the server considers trusted.
     756             :  * This is a hint and typically the client should send a certificate that is signed
     757             :  * by one of these CAs. These names, when available, are DER encoded. To get a more
     758             :  * meaningful value use the function gnutls_x509_rdn_get().
     759             :  *
     760             :  * @pk_algos contains a list with server's acceptable public key algorithms.
     761             :  * The certificate returned should support the server's given algorithms.
     762             :  *
     763             :  * @pcert should contain a single certificate and public key or a list of them.
     764             :  *
     765             :  * @pcert_length is the size of the previous list.
     766             :  *
     767             :  * @pkey is the private key.
     768             :  *
     769             :  * If the callback function is provided then gnutls will call it, in the
     770             :  * handshake, after the certificate request message has been received.
     771             :  * All the provided by the callback values will not be released or
     772             :  * modified by gnutls.
     773             :  *
     774             :  * In server side pk_algos and req_ca_dn are NULL.
     775             :  *
     776             :  * The callback function should set the certificate list to be sent,
     777             :  * and return 0 on success. If no certificate was selected then the
     778             :  * number of certificates should be set to zero. The value (-1)
     779             :  * indicates error and the handshake will be terminated. If both certificates
     780             :  * are set in the credentials and a callback is available, the callback
     781             :  * takes predence.
     782             :  *
     783             :  * Since: 3.0
     784             :  **/
     785         324 : void gnutls_certificate_set_retrieve_function2
     786             :     (gnutls_certificate_credentials_t cred,
     787             :      gnutls_certificate_retrieve_function2 * func)
     788             : {
     789         324 :         cred->legacy_cert_cb2 = func;
     790         324 :         if (!func)
     791           1 :                 cred->get_cert_callback3 = NULL;
     792             :         else
     793         323 :                 cred->get_cert_callback3 = call_legacy_cert_cb2;
     794         324 : }
     795             : 
     796             : /**
     797             :  * gnutls_certificate_set_retrieve_function3:
     798             :  * @cred: is a #gnutls_certificate_credentials_t type.
     799             :  * @func: is the callback function
     800             :  *
     801             :  * This function sets a callback to be called in order to retrieve the
     802             :  * certificate and OCSP responses to be used in the handshake. @func will
     803             :  * be called only if the peer requests a certificate either during handshake
     804             :  * or during post-handshake authentication.
     805             :  *
     806             :  * The callback's function prototype is defined in `abstract.h':
     807             :  *
     808             :  * int gnutls_certificate_retrieve_function3(
     809             :  * gnutls_session_t,
     810             :  * const struct gnutls_cert_retr_st *info,
     811             :  * gnutls_pcert_st **certs,
     812             :  * unsigned int *pcert_length,
     813             :  * gnutls_ocsp_data_st **ocsp,
     814             :  * unsigned int *ocsp_length,
     815             :  * gnutls_privkey_t *privkey,
     816             :  * unsigned int *flags);
     817             :  *
     818             :  * The info field of the callback contains:
     819             :  * @req_ca_dn which is a list with the CA names that the server considers trusted.
     820             :  * This is a hint and typically the client should send a certificate that is signed
     821             :  * by one of these CAs. These names, when available, are DER encoded. To get a more
     822             :  * meaningful value use the function gnutls_x509_rdn_get().
     823             :  * @pk_algos contains a list with server's acceptable public key algorithms.
     824             :  * The certificate returned should support the server's given algorithms.
     825             :  *
     826             :  * The callback should fill-in the following values.
     827             :  *
     828             :  * @pcert should contain an allocated list of certificates and public keys.
     829             :  * @pcert_length is the size of the previous list.
     830             :  * @ocsp should contain an allocated list of OCSP responses.
     831             :  * @ocsp_length is the size of the previous list.
     832             :  * @pkey is the private key.
     833             :  *
     834             :  * If flags in the callback are set to %GNUTLS_CERT_RETR_DEINIT_ALL then
     835             :  * all provided values must be allocated using gnutls_malloc(), and will
     836             :  * be released by gnutls; otherwise they will not be touched by gnutls.
     837             :  *
     838             :  * The callback function should set the certificate and OCSP response
     839             :  * list to be sent, and return 0 on success. If no certificates are available,
     840             :  * the @pcert_length and @ocsp_length should be set to zero. The return
     841             :  * value (-1) indicates error and the handshake will be terminated. If both
     842             :  * certificates are set in the credentials and a callback is available, the
     843             :  * callback takes predence.
     844             :  *
     845             :  * Since: 3.6.3
     846             :  **/
     847           7 : void gnutls_certificate_set_retrieve_function3
     848             :     (gnutls_certificate_credentials_t cred,
     849             :      gnutls_certificate_retrieve_function3 *func)
     850             : {
     851           7 :         cred->get_cert_callback3 = func;
     852           7 : }
     853             : 
     854             : /**
     855             :  * gnutls_certificate_set_verify_function:
     856             :  * @cred: is a #gnutls_certificate_credentials_t type.
     857             :  * @func: is the callback function
     858             :  *
     859             :  * This function sets a callback to be called when peer's certificate
     860             :  * has been received in order to verify it on receipt rather than
     861             :  * doing after the handshake is completed.
     862             :  *
     863             :  * The callback's function prototype is:
     864             :  * int (*callback)(gnutls_session_t);
     865             :  *
     866             :  * If the callback function is provided then gnutls will call it, in the
     867             :  * handshake, just after the certificate message has been received.
     868             :  * To verify or obtain the certificate the gnutls_certificate_verify_peers2(),
     869             :  * gnutls_certificate_type_get(), gnutls_certificate_get_peers() functions
     870             :  * can be used.
     871             :  *
     872             :  * The callback function should return 0 for the handshake to continue
     873             :  * or non-zero to terminate.
     874             :  *
     875             :  * Since: 2.10.0
     876             :  **/
     877             : void
     878       10458 :  gnutls_certificate_set_verify_function
     879             :     (gnutls_certificate_credentials_t cred,
     880             :      gnutls_certificate_verify_function * func)
     881             : {
     882       10458 :         cred->verify_callback = func;
     883       10458 : }
     884             : 
     885             : /**
     886             :  * gnutls_x509_trust_list_set_getissuer_function:
     887             :  * @tlist: is a #gnutls_x509_trust_list_t type.
     888             :  * @func: is the callback function
     889             :  *
     890             :  * This function sets a callback to be called when the peer's certificate
     891             :  * chain is incomplete due a missing intermediate certificate/certificates.
     892             :  *
     893             :  * The callback's function prototype is defined in `abstract.h':
     894             :  * int (*callback)(
     895             :  * gnutls_x509_trust_list_t tlist,
     896             :  * const gnutls_x509_crt_t crt);
     897             :  *
     898             :  * If the callback function is provided then gnutls will call it, in the
     899             :  * certificate verification procedure.
     900             :  * To verify or obtain the certificate the verification functions such as
     901             :  * gnutls_x509_trust_list_verify_crt() and gnutls_x509_trust_list_verify_crt2()
     902             :  * can be used.
     903             :  *
     904             :  * The callback function should return 0 if the missing issuer certificate
     905             :  * for 'crt' was properly populated and added to the 'tlist' using
     906             :  * gnutls_x509_trust_list_add_cas() or non-zero to continue the certificate list
     907             :  * verification but with issuer as %NULL.
     908             :  *
     909             :  * Since: 3.7.0
     910             :  **/
     911           2 : void gnutls_x509_trust_list_set_getissuer_function(gnutls_x509_trust_list_t tlist,
     912             :                 gnutls_x509_trust_list_getissuer_function * func)
     913             : {
     914           2 :         tlist->issuer_callback = func;
     915           2 : }
     916             : 
     917             : /**
     918             :  * gnutls_x509_trust_list_set_ptr:
     919             :  * @tlist: is a #gnutls_x509_trust_list_t type.
     920             :  * @ptr: is the user pointer
     921             :  *
     922             :  * This function will set (associate) the user given pointer @ptr to
     923             :  * the tlist structure. This pointer can be accessed with
     924             :  * gnutls_x509_trust_list_get_ptr(). Useful in the callback function
     925             :  * gnutls_x509_trust_list_set_getissuer_function.
     926             :  *
     927             :  * Since: 3.7.0
     928             :  **/
     929           0 : void gnutls_x509_trust_list_set_ptr(gnutls_x509_trust_list_t tlist, void *ptr)
     930             : {
     931           0 :         tlist->usr_ptr = ptr;
     932           0 : }
     933             : 
     934             : /**
     935             :  * gnutls_x509_trust_list_get_ptr:
     936             :  * @tlist: is a #gnutls_x509_trust_list_t type.
     937             :  *
     938             :  * Get user pointer for tlist. Useful in callback function
     939             :  * gnutls_x509_trust_list_set_getissuer_function.
     940             :  * This is the pointer set with gnutls_x509_trust_list_set_ptr().
     941             :  *
     942             :  * Returns: the user given pointer from the tlist structure, or
     943             :  *   %NULL if it was never set.
     944             :  *
     945             :  * Since: 3.7.0
     946             :  **/
     947           0 : void *gnutls_x509_trust_list_get_ptr(gnutls_x509_trust_list_t tlist)
     948             : {
     949           0 :         return tlist->usr_ptr;
     950             : }
     951             : 
     952             : #define TEST_TEXT "test text"
     953             : /* returns error if the certificate has different algorithm than
     954             :  * the given key parameters.
     955             :  */
     956       11343 : int _gnutls_check_key_cert_match(gnutls_certificate_credentials_t res)
     957             : {
     958       11343 :         gnutls_datum_t test = {(void*)TEST_TEXT, sizeof(TEST_TEXT)-1};
     959       11343 :         gnutls_datum_t sig = {NULL, 0};
     960       11343 :         gnutls_digest_algorithm_t dig;
     961       11343 :         int pk, pk2, ret;
     962       11343 :         unsigned sign_algo;
     963             : 
     964       11343 :         if (res->flags & GNUTLS_CERTIFICATE_SKIP_KEY_CERT_MATCH)
     965             :                 return 0;
     966             : 
     967       11340 :         pk =
     968       11340 :             gnutls_pubkey_get_pk_algorithm(res->certs[res->ncerts - 1].
     969             :                                            cert_list[0].pubkey, NULL);
     970       11340 :         pk2 =
     971       11340 :             gnutls_privkey_get_pk_algorithm(res->certs[res->ncerts - 1].pkey,
     972             :                                             NULL);
     973             : 
     974       11340 :         if (GNUTLS_PK_IS_RSA(pk) && GNUTLS_PK_IS_RSA(pk2)) {
     975        4493 :                 if (pk2 == GNUTLS_PK_RSA_PSS && pk == GNUTLS_PK_RSA) {
     976           0 :                         _gnutls_debug_log("you cannot mix an RSA-PSS key with an RSA certificate\n");
     977           0 :                         return GNUTLS_E_CERTIFICATE_KEY_MISMATCH;
     978             :                 }
     979             : 
     980        4493 :                 if (pk2 == GNUTLS_PK_RSA_PSS || pk == GNUTLS_PK_RSA_PSS)
     981             :                         pk = GNUTLS_PK_RSA_PSS;
     982        6847 :         } else if (pk2 != pk) {
     983           2 :                 gnutls_assert();
     984           2 :                 _gnutls_debug_log("key is %s, certificate is %s\n", gnutls_pk_get_name(pk2),
     985             :                         gnutls_pk_get_name(pk));
     986           2 :                 return GNUTLS_E_CERTIFICATE_KEY_MISMATCH;
     987             :         }
     988             : 
     989       11293 :         if (pk == GNUTLS_PK_GOST_01)
     990             :                 dig = GNUTLS_DIG_GOSTR_94;
     991       11338 :         else if (pk == GNUTLS_PK_GOST_12_256)
     992             :                 dig = GNUTLS_DIG_STREEBOG_256;
     993       11327 :         else if (pk == GNUTLS_PK_GOST_12_512)
     994             :                 dig = GNUTLS_DIG_STREEBOG_512;
     995             :         else
     996       11315 :                 dig = GNUTLS_DIG_SHA256;
     997             : 
     998       11338 :         sign_algo = gnutls_pk_to_sign(pk, dig);
     999             : 
    1000             :         /* now check if keys really match. We use the sign/verify approach
    1001             :          * because we cannot always obtain the parameters from the abstract
    1002             :          * keys (e.g. PKCS #11). */
    1003       11338 :         ret = gnutls_privkey_sign_data2(res->certs[res->ncerts - 1].pkey,
    1004             :                 sign_algo, 0, &test, &sig);
    1005       11338 :         if (ret < 0) {
    1006             :                 /* for some reason we couldn't sign that. That shouldn't have
    1007             :                  * happened, but since it did, report the issue and do not
    1008             :                  * try the key matching test */
    1009        4074 :                 _gnutls_debug_log("%s: failed signing\n", __func__);
    1010        4074 :                 goto finish;
    1011             :         }
    1012             : 
    1013        7264 :         ret = gnutls_pubkey_verify_data2(res->certs[res->ncerts - 1].cert_list[0].pubkey,
    1014             :                                          sign_algo,
    1015             :                                          GNUTLS_VERIFY_ALLOW_BROKEN, &test, &sig);
    1016             : 
    1017        7264 :         gnutls_free(sig.data);
    1018             : 
    1019        7264 :         if (ret < 0)
    1020           1 :                 return gnutls_assert_val(GNUTLS_E_CERTIFICATE_KEY_MISMATCH);
    1021             : 
    1022        7263 :  finish:
    1023             :         return 0;
    1024             : }
    1025             : 
    1026             : /**
    1027             :  * gnutls_certificate_verification_status_print:
    1028             :  * @status: The status flags to be printed
    1029             :  * @type: The certificate type
    1030             :  * @out: Newly allocated datum with (0) terminated string.
    1031             :  * @flags: should be zero
    1032             :  *
    1033             :  * This function will pretty print the status of a verification
    1034             :  * process -- eg. the one obtained by gnutls_certificate_verify_peers3().
    1035             :  *
    1036             :  * The output @out needs to be deallocated using gnutls_free().
    1037             :  *
    1038             :  * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise a
    1039             :  *   negative error value.
    1040             :  *
    1041             :  * Since: 3.1.4
    1042             :  **/
    1043             : int
    1044         777 : gnutls_certificate_verification_status_print(unsigned int status,
    1045             :                                              gnutls_certificate_type_t
    1046             :                                              type, gnutls_datum_t * out,
    1047             :                                              unsigned int flags)
    1048             : {
    1049         777 :         gnutls_buffer_st str;
    1050             : 
    1051         777 :         _gnutls_buffer_init(&str);
    1052             : 
    1053         777 :         if (status == 0)
    1054         497 :                 _gnutls_buffer_append_str(&str,
    1055         497 :                                           _
    1056             :                                           ("The certificate is trusted. "));
    1057             :         else
    1058         280 :                 _gnutls_buffer_append_str(&str,
    1059         280 :                                           _
    1060             :                                           ("The certificate is NOT trusted. "));
    1061             : 
    1062         777 :         if (type == GNUTLS_CRT_X509) {
    1063         777 :                 if (status & GNUTLS_CERT_REVOKED)
    1064          12 :                         _gnutls_buffer_append_str(&str,
    1065          12 :                                                   _
    1066             :                                                   ("The certificate chain is revoked. "));
    1067             : 
    1068         777 :                 if (status & GNUTLS_CERT_MISMATCH)
    1069           0 :                         _gnutls_buffer_append_str(&str,
    1070           0 :                                                   _
    1071             :                                                   ("The certificate doesn't match the local copy (TOFU). "));
    1072             : 
    1073         777 :                 if (status & GNUTLS_CERT_REVOCATION_DATA_SUPERSEDED)
    1074           2 :                         _gnutls_buffer_append_str(&str,
    1075           2 :                                                   _
    1076             :                                                   ("The revocation or OCSP data are old and have been superseded. "));
    1077             : 
    1078         777 :                 if (status & GNUTLS_CERT_REVOCATION_DATA_ISSUED_IN_FUTURE)
    1079           0 :                         _gnutls_buffer_append_str(&str,
    1080           0 :                                                   _
    1081             :                                                   ("The revocation or OCSP data are issued with a future date. "));
    1082             : 
    1083         777 :                 if (status & GNUTLS_CERT_SIGNER_NOT_FOUND)
    1084         181 :                         _gnutls_buffer_append_str(&str,
    1085         181 :                                                   _
    1086             :                                                   ("The certificate issuer is unknown. "));
    1087             : 
    1088         777 :                 if (status & GNUTLS_CERT_SIGNER_NOT_CA)
    1089           8 :                         _gnutls_buffer_append_str(&str,
    1090           8 :                                                   _
    1091             :                                                   ("The certificate issuer is not a CA. "));
    1092             :         }
    1093             : 
    1094         777 :         if (status & GNUTLS_CERT_INSECURE_ALGORITHM)
    1095          34 :                 _gnutls_buffer_append_str(&str,
    1096          34 :                                           _
    1097             :                                           ("The certificate chain uses insecure algorithm. "));
    1098             : 
    1099         777 :         if (status & GNUTLS_CERT_SIGNER_CONSTRAINTS_FAILURE)
    1100          25 :                 _gnutls_buffer_append_str(&str,
    1101          25 :                                           _
    1102             :                                           ("The certificate chain violates the signer's constraints. "));
    1103             : 
    1104         777 :         if (status & GNUTLS_CERT_PURPOSE_MISMATCH)
    1105           0 :                 _gnutls_buffer_append_str(&str,
    1106           0 :                                           _
    1107             :                                           ("The certificate chain does not match the intended purpose. "));
    1108             : 
    1109         777 :         if (status & GNUTLS_CERT_NOT_ACTIVATED)
    1110           6 :                 _gnutls_buffer_append_str(&str,
    1111           6 :                                           _
    1112             :                                           ("The certificate chain uses not yet valid certificate. "));
    1113             : 
    1114         777 :         if (status & GNUTLS_CERT_EXPIRED)
    1115          28 :                 _gnutls_buffer_append_str(&str,
    1116          28 :                                           _
    1117             :                                           ("The certificate chain uses expired certificate. "));
    1118             : 
    1119         777 :         if (status & GNUTLS_CERT_SIGNATURE_FAILURE)
    1120          12 :                 _gnutls_buffer_append_str(&str,
    1121          12 :                                           _
    1122             :                                           ("The signature in the certificate is invalid. "));
    1123             : 
    1124         777 :         if (status & GNUTLS_CERT_UNEXPECTED_OWNER)
    1125         146 :                 _gnutls_buffer_append_str(&str,
    1126         146 :                                           _
    1127             :                                           ("The name in the certificate does not match the expected. "));
    1128             : 
    1129         777 :         if (status & GNUTLS_CERT_MISSING_OCSP_STATUS)
    1130           2 :                 _gnutls_buffer_append_str(&str,
    1131           2 :                                           _
    1132             :                                           ("The certificate requires the server to include an OCSP status in its response, but the OCSP status is missing. "));
    1133             : 
    1134         777 :         if (status & GNUTLS_CERT_INVALID_OCSP_STATUS)
    1135           3 :                 _gnutls_buffer_append_str(&str,
    1136           3 :                                           _
    1137             :                                           ("The received OCSP status response is invalid. "));
    1138             : 
    1139         777 :         if (status & GNUTLS_CERT_UNKNOWN_CRIT_EXTENSIONS)
    1140          15 :                 _gnutls_buffer_append_str(&str,
    1141          15 :                                           _
    1142             :                                           ("The certificate contains an unknown critical extension. "));
    1143             : 
    1144         777 :         return _gnutls_buffer_to_datum(&str, out, 1);
    1145             : }
    1146             : 
    1147             : #if defined(ENABLE_DHE) || defined(ENABLE_ANON)
    1148             : /**
    1149             :  * gnutls_certificate_set_dh_params:
    1150             :  * @res: is a gnutls_certificate_credentials_t type
    1151             :  * @dh_params: the Diffie-Hellman parameters.
    1152             :  *
    1153             :  * This function will set the Diffie-Hellman parameters for a
    1154             :  * certificate server to use. These parameters will be used in
    1155             :  * Ephemeral Diffie-Hellman cipher suites.  Note that only a pointer
    1156             :  * to the parameters are stored in the certificate handle, so you
    1157             :  * must not deallocate the parameters before the certificate is deallocated.
    1158             :  *
    1159             :  * Deprecated: This function is unnecessary and discouraged on GnuTLS 3.6.0
    1160             :  * or later. Since 3.6.0, DH parameters are negotiated
    1161             :  * following RFC7919.
    1162             :  *
    1163             :  **/
    1164             : void
    1165         228 : gnutls_certificate_set_dh_params(gnutls_certificate_credentials_t res,
    1166             :                                  gnutls_dh_params_t dh_params)
    1167             : {
    1168         228 :         if (res->deinit_dh_params) {
    1169           0 :                 res->deinit_dh_params = 0;
    1170           0 :                 gnutls_dh_params_deinit(res->dh_params);
    1171           0 :                 res->dh_params = NULL;
    1172             :         }
    1173             : 
    1174         228 :         res->dh_params = dh_params;
    1175         228 :         res->dh_sec_param = gnutls_pk_bits_to_sec_param(GNUTLS_PK_DH, _gnutls_mpi_get_nbits(dh_params->params[0]));
    1176         228 : }
    1177             : 
    1178             : 
    1179             : /**
    1180             :  * gnutls_certificate_set_known_dh_params:
    1181             :  * @res: is a gnutls_certificate_credentials_t type
    1182             :  * @sec_param: is an option of the %gnutls_sec_param_t enumeration
    1183             :  *
    1184             :  * This function will set the Diffie-Hellman parameters for a
    1185             :  * certificate server to use. These parameters will be used in
    1186             :  * Ephemeral Diffie-Hellman cipher suites and will be selected from
    1187             :  * the FFDHE set of RFC7919 according to the security level provided.
    1188             :  *
    1189             :  * Deprecated: This function is unnecessary and discouraged on GnuTLS 3.6.0
    1190             :  * or later. Since 3.6.0, DH parameters are negotiated
    1191             :  * following RFC7919.
    1192             :  *
    1193             :  * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise a
    1194             :  *   negative error value.
    1195             :  *
    1196             :  * Since: 3.5.6
    1197             :  **/
    1198             : int
    1199        2672 : gnutls_certificate_set_known_dh_params(gnutls_certificate_credentials_t res,
    1200             :                                        gnutls_sec_param_t sec_param)
    1201             : {
    1202        2672 :         res->dh_sec_param = sec_param;
    1203             : 
    1204        2672 :         return 0;
    1205             : }
    1206             : 
    1207             : #endif                          /* DH */

Generated by: LCOV version 1.14