Next: SRP credentials, Up: Associating the credentials [Contents][Index]
When using certificates the server is required to have at least one certificate and private key pair. Clients may not hold such a pair, but a server could require it. In this section we discuss general issues applying to both client and server certificates. The next section will elaborate on issues arising from client authentication only.
int gnutls_certificate_allocate_credentials (gnutls_certificate_credentials_t * res)
void gnutls_certificate_free_credentials (gnutls_certificate_credentials_t sc)
After the credentials structures are initialized, the certificate and key pair must be loaded. This occurs before any TLS session is initialized, and the same structures are reused for multiple sessions. Depending on the certificate type different loading functions are available, as shown below. For X.509 certificates, the functions will accept and use a certificate chain that leads to a trusted authority. The certificate chain must be ordered in such way that every certificate certifies the one before it. The trusted authority’s certificate need not to be included since the peer should possess it already.
int gnutls_certificate_set_x509_key_mem2 (gnutls_certificate_credentials_t res, const gnutls_datum_t * cert, const gnutls_datum_t * key, gnutls_x509_crt_fmt_t type, const char* pass, unsigned int flags)
int gnutls_certificate_set_x509_key (gnutls_certificate_credentials_t res, gnutls_x509_crt_t * cert_list, int cert_list_size, gnutls_x509_privkey_t key)
int gnutls_certificate_set_x509_key_file2 (gnutls_certificate_credentials_t res, const char * certfile, const char * keyfile, gnutls_x509_crt_fmt_t type, const char* pass, unsigned int flags)
int gnutls_certificate_set_openpgp_key_mem (gnutls_certificate_credentials_t res, const gnutls_datum_t * cert, const gnutls_datum_t * key, gnutls_openpgp_crt_fmt_t format)
int gnutls_certificate_set_openpgp_key (gnutls_certificate_credentials_t res, gnutls_openpgp_crt_t crt, gnutls_openpgp_privkey_t pkey)
int gnutls_certificate_set_openpgp_key_file (gnutls_certificate_credentials_t res, const char * certfile, const char * keyfile, gnutls_openpgp_crt_fmt_t format)
Note however, that since functions like gnutls_certificate_set_x509_key_file2 may accept URLs that specify objects stored in token, another important function is gnutls_certificate_set_pin_function. That allows setting a callback function to retrieve a PIN if the input keys are protected by PIN by the token.
cred: is a gnutls_certificate_credentials_t
structure.
fn: A PIN callback
userdata: Data to be passed in the callback
This function will set a callback function to be used when required to access a protected object. This function overrides any other global PIN functions.
Note that this function must be called right after initialization to have effect.
Since: 3.1.0
If the imported keys and certificates need to be accessed before any TLS session is established, it is convenient to use gnutls_certificate_set_key in combination with gnutls_pcert_import_x509_raw and gnutls_privkey_import_x509_raw.
res: is a gnutls_certificate_credentials_t
structure.
names: is an array of DNS name of the certificate (NULL if none)
names_size: holds the size of the names list
pcert_list: contains a certificate list (path) for the specified private key
pcert_list_size: holds the size of the certificate list
key: is a gnutls_privkey_t
key
This function sets a certificate/private key pair in the
gnutls_certificate_credentials_t structure. This function may be
called more than once, in case multiple keys/certificates exist for
the server. For clients that wants to send more than its own end
entity certificate (e.g., also an intermediate CA cert) then put
the certificate chain in pcert_list
.
Note that the pcert_list
and key
will become part of the credentials
structure and must not be deallocated. They will be automatically deallocated
when the res
structure is deinitialized.
Returns: GNUTLS_E_SUCCESS
(0) on success, or a negative error code.
Since: 3.0
If multiple certificates are used with the functions above each client’s request will be served with the certificate that matches the requested name (see Server name indication).
As an alternative to loading from files or buffers, a callback may be used for the server or the client to specify the certificate and the key at the handshake time. In that case a certificate should be selected according the peer’s signature algorithm preferences. To get those preferences use gnutls_sign_algorithm_get_requested. Both functions are shown below.
void gnutls_certificate_set_retrieve_function (gnutls_certificate_credentials_t cred, gnutls_certificate_retrieve_function * func)
void gnutls_certificate_set_retrieve_function2 (gnutls_certificate_credentials_t cred, gnutls_certificate_retrieve_function2 * func)
int gnutls_sign_algorithm_get_requested (gnutls_session_t session, size_t indx, gnutls_sign_algorithm_t * algo)
The functions above do not handle the requested server name automatically.
A server would need to check the name requested by the client
using gnutls_server_name_get, and serve the appropriate
certificate. Note that some of these functions require the gnutls_pcert_st
structure to be
filled in. Helper functions to make the required structures are listed below.
typedef struct gnutls_pcert_st { gnutls_pubkey_t pubkey; gnutls_datum_t cert; gnutls_certificate_type_t type; } gnutls_pcert_st;
int gnutls_pcert_import_x509 (gnutls_pcert_st* pcert, gnutls_x509_crt_t crt, unsigned int flags)
int gnutls_pcert_import_openpgp (gnutls_pcert_st* pcert, gnutls_openpgp_crt_t crt, unsigned int flags)
int gnutls_pcert_import_x509_raw (gnutls_pcert_st * pcert, const gnutls_datum_t* cert, gnutls_x509_crt_fmt_t format, unsigned int flags)
int gnutls_pcert_import_openpgp_raw (gnutls_pcert_st * pcert, const gnutls_datum_t* cert, gnutls_openpgp_crt_fmt_t format, gnutls_openpgp_keyid_t keyid, unsigned int flags)
void gnutls_pcert_deinit (gnutls_pcert_st * pcert)
In a handshake, the negotiated cipher suite depends on the
certificate’s parameters, so some key exchange methods might not be
available with all certificates. GnuTLS will disable
ciphersuites that are not compatible with the key, or the enabled
authentication methods. For example keys marked as sign-only, will
not be able to access the plain RSA ciphersuites, that require
decryption. It is not recommended to use RSA keys for both
signing and encryption. If possible use a different key for the
DHE-RSA
which uses signing and RSA
that requires decryption.
All the key exchange methods shown in Table 4.1 are
available in certificate authentication.
If a certificate is to be requested from the client during the handshake, the server will send a certificate request message. This behavior is controlled gnutls_certificate_server_set_request. The request contains a list of the acceptable by the server certificate signers. This list is constructed using the trusted certificate authorities of the server. In cases where the server supports a large number of certificate authorities it makes sense not to advertise all of the names to save bandwidth. That can be controlled using the function gnutls_certificate_send_x509_rdn_sequence. This however will have the side-effect of not restricting the client to certificates signed by server’s acceptable signers.
session: is a gnutls_session_t
structure.
req: is one of GNUTLS_CERT_REQUEST, GNUTLS_CERT_REQUIRE
This function specifies if we (in case of a server) are going to
send a certificate request message to the client. If req
is
GNUTLS_CERT_REQUIRE then the server will return an error if the
peer does not provide a certificate. If you do not call this
function then the client will not be asked to send a certificate.
session: is a pointer to a gnutls_session_t
structure.
status: is 0 or 1
If status is non zero, this function will order gnutls not to send the rdnSequence in the certificate request message. That is the server will not advertise its trusted CAs to the peer. If status is zero then the default behaviour will take effect, which is to advertise the server’s trusted CAs.
This function has no effect in clients, and in authentication methods other than certificate with X.509 certificates.
Certificate verification is possible by loading the trusted authorities into the credentials structure by using the following functions, applicable to X.509 and OpenPGP certificates.
int gnutls_certificate_set_x509_system_trust (gnutls_certificate_credentials_t cred)
int gnutls_certificate_set_x509_trust_file (gnutls_certificate_credentials_t cred, const char * cafile, gnutls_x509_crt_fmt_t type)
int gnutls_certificate_set_openpgp_keyring_file (gnutls_certificate_credentials_t c, const char * file, gnutls_openpgp_crt_fmt_t format)
The peer’s certificate is not automatically verified and one must call gnutls_certificate_verify_peers3 after a successful handshake to verify the certificate’s signature and the owner of the certificate. The verification status returned can be printed using gnutls_certificate_verification_status_print.
Alternatively the verification can occur during the handshake by using gnutls_certificate_set_verify_function.
The functions above provide a brief verification output. If a detailed output is required one should call gnutls_certificate_get_peers to obtain the raw certificate of the peer and verify it using the functions discussed in X.509 certificates.
session: is a gnutls session
hostname: is the expected name of the peer; may be NULL
status: is the output of the verification
This function will verify the peer’s certificate and store the
status in the status
variable as a bitwise or’d gnutls_certificate_status_t
values or zero if the certificate is trusted. Note that value in status
is set only when the return value of this function is success (i.e, failure
to trust a certificate does not imply a negative return value).
If the hostname
provided is non-NULL then this function will compare
the hostname in the certificate against the given. If they do not match
the GNUTLS_CERT_UNEXPECTED_OWNER
status flag will be set.
If available the OCSP Certificate Status extension will be utilized by this function.
To avoid denial of service attacks some
default upper limits regarding the certificate key size and chain
size are set. To override them use gnutls_certificate_set_verify_limits()
.
Returns: a negative error code on error and GNUTLS_E_SUCCESS
(0) on success.
Since: 3.1.4
cred: is a gnutls_certificate_credentials_t
structure.
func: is the callback function
This function sets a callback to be called when peer’s certificate has been received in order to verify it on receipt rather than doing after the handshake is completed.
The callback’s function prototype is: int (*callback)(gnutls_session_t);
If the callback function is provided then gnutls will call it, in the
handshake, just after the certificate message has been received.
To verify or obtain the certificate the gnutls_certificate_verify_peers2()
,
gnutls_certificate_type_get()
, gnutls_certificate_get_peers()
functions
can be used.
The callback function should return 0 for the handshake to continue or non-zero to terminate.
Since: 2.10.0
Next: SRP credentials, Up: Associating the credentials [Contents][Index]