mirror of
https://gitlab.com/openconnect/ocserv.git
synced 2026-02-10 00:37:00 +08:00
When renegotiating, verify that any certificate received from the client contains the same username.
This commit is contained in:
30
src/tlslib.c
30
src/tlslib.c
@@ -245,11 +245,35 @@ static int verify_certificate_cb(gnutls_session_t session)
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (session == ws->dtls_session) /* no certificate is verified in DTLS */
|
||||
return 0;
|
||||
if (session == ws->dtls_session) {
|
||||
oclog(ws, LOG_ERR, "unexpected issue; client shouldn't have offered a certificate in DTLS");
|
||||
return GNUTLS_E_CERTIFICATE_ERROR;
|
||||
}
|
||||
|
||||
ws->cert_auth_ok = 0;
|
||||
|
||||
/* now verify whether the username in the certificate matches the username of the session */
|
||||
if (ws->cert_username[0] != 0) {
|
||||
char prev_username[MAX_USERNAME_SIZE];
|
||||
const gnutls_datum_t *cert;
|
||||
unsigned cert_size;
|
||||
|
||||
cert = gnutls_certificate_get_peers(session, &cert_size);
|
||||
if (cert != NULL) { /* it's ok for the user not to send any certificate on renegotiation */
|
||||
memcpy(prev_username, ws->cert_username, MAX_USERNAME_SIZE);
|
||||
ret = get_cert_names(ws, &cert[0]);
|
||||
if (ret < 0) {
|
||||
oclog(ws, LOG_ERR, "cannot parse certificate");
|
||||
return GNUTLS_E_CERTIFICATE_ERROR;
|
||||
}
|
||||
|
||||
if (strcmp(prev_username, ws->cert_username) != 0) {
|
||||
oclog(ws, LOG_ERR, "user switched during renegotiation!");
|
||||
return GNUTLS_E_CERTIFICATE_ERROR;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* This verification function uses the trusted CAs in the credentials
|
||||
* structure. So you must have installed one or more CA certificates.
|
||||
*/
|
||||
@@ -282,6 +306,8 @@ static int verify_certificate_cb(gnutls_session_t session)
|
||||
/* notify gnutls to continue handshake normally */
|
||||
return 0;
|
||||
fail:
|
||||
/* In cisco client compatibility we don't hangup immediately, we
|
||||
* simply use the flag (ws->cert_auth_ok). */
|
||||
if (ws->config->cisco_client_compat == 0)
|
||||
return GNUTLS_E_CERTIFICATE_ERROR;
|
||||
else
|
||||
|
||||
@@ -378,7 +378,6 @@ int get_auth_handler(worker_st * ws, unsigned http_ver)
|
||||
return get_auth_handler2(ws, http_ver, NULL);
|
||||
}
|
||||
|
||||
static
|
||||
int get_cert_names(worker_st * ws, const gnutls_datum_t * raw)
|
||||
{
|
||||
gnutls_x509_crt_t crt;
|
||||
|
||||
@@ -246,6 +246,7 @@ int get_empty_handler(worker_st *server, unsigned http_ver);
|
||||
int get_config_handler(worker_st *ws, unsigned http_ver);
|
||||
int get_string_handler(worker_st *ws, unsigned http_ver);
|
||||
int get_dl_handler(worker_st *ws, unsigned http_ver);
|
||||
int get_cert_names(worker_st * ws, const gnutls_datum_t * raw);
|
||||
|
||||
void set_resume_db_funcs(gnutls_session_t);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user