X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=lib%2Fstream-ssl.c;h=51ce306353f0351fac5972b5bbb3ccfff7df2362;hb=f479c2f42b01cbb6fb0a60448f314021b1c3c9df;hp=442a1e6a519423da7a9fe153bde449c8fac44520;hpb=36775dad3505929f8370166c33e8e0f04ca96c1c;p=openvswitch diff --git a/lib/stream-ssl.c b/lib/stream-ssl.c index 442a1e6a..51ce3063 100644 --- a/lib/stream-ssl.c +++ b/lib/stream-ssl.c @@ -155,7 +155,7 @@ static void ssl_close(struct stream *); static void ssl_clear_txbuf(struct ssl_stream *); static int interpret_ssl_error(const char *function, int ret, int error, int *want); -static DH *tmp_dh_callback(SSL *ssl, int is_export UNUSED, int keylength); +static DH *tmp_dh_callback(SSL *ssl, int is_export OVS_UNUSED, int keylength); static void log_ca_cert(const char *file_name, X509 *cert); static short int @@ -437,6 +437,14 @@ ssl_close(struct stream *stream) { struct ssl_stream *sslv = ssl_stream_cast(stream); ssl_clear_txbuf(sslv); + + /* Attempt clean shutdown of the SSL connection. This will work most of + * the time, as long as the kernel send buffer has some free space and the + * SSL connection isn't renegotiating, etc. That has to be good enough, + * since we don't have any way to continue the close operation in the + * background. */ + SSL_shutdown(sslv->ssl); + SSL_free(sslv->ssl); close(sslv->fd); free(sslv); @@ -541,7 +549,8 @@ ssl_recv(struct stream *stream, void *buffer, size_t n) if (error == SSL_ERROR_ZERO_RETURN) { return 0; } else { - return interpret_ssl_error("SSL_read", ret, error, &sslv->rx_want); + return -interpret_ssl_error("SSL_read", ret, error, + &sslv->rx_want); } } } @@ -589,7 +598,7 @@ ssl_send(struct stream *stream, const void *buffer, size_t n) struct ssl_stream *sslv = ssl_stream_cast(stream); if (sslv->txbuf) { - return EAGAIN; + return -EAGAIN; } else { int error; @@ -598,13 +607,13 @@ ssl_send(struct stream *stream, const void *buffer, size_t n) switch (error) { case 0: ssl_clear_txbuf(sslv); - return 0; + return n; case EAGAIN: leak_checker_claim(buffer); - return 0; + return n; default: sslv->txbuf = NULL; - return error; + return -error; } } } @@ -710,9 +719,11 @@ pssl_pstream_cast(struct pstream *pstream) } static int -pssl_open(const char *name, char *suffix, struct pstream **pstreamp) +pssl_open(const char *name OVS_UNUSED, char *suffix, struct pstream **pstreamp) { struct pssl_pstream *pssl; + struct sockaddr_in sin; + char bound_name[128]; int retval; int fd; @@ -721,13 +732,15 @@ pssl_open(const char *name, char *suffix, struct pstream **pstreamp) return retval; } - fd = inet_open_passive(SOCK_STREAM, suffix, OFP_SSL_PORT, NULL); + fd = inet_open_passive(SOCK_STREAM, suffix, OFP_SSL_PORT, &sin); if (fd < 0) { return -fd; } + sprintf(bound_name, "pssl:%"PRIu16":"IP_FMT, + ntohs(sin.sin_port), IP_ARGS(&sin.sin_addr.s_addr)); pssl = xmalloc(sizeof *pssl); - pstream_init(&pssl->pstream, &pssl_pstream_class, name); + pstream_init(&pssl->pstream, &pssl_pstream_class, bound_name); pssl->fd = fd; *pstreamp = &pssl->pstream; return 0; @@ -842,7 +855,7 @@ do_ssl_init(void) } static DH * -tmp_dh_callback(SSL *ssl UNUSED, int is_export UNUSED, int keylength) +tmp_dh_callback(SSL *ssl OVS_UNUSED, int is_export OVS_UNUSED, int keylength) { struct dh { int keylength; @@ -1061,6 +1074,7 @@ stream_ssl_set_ca_cert_file(const char *file_name, bool bootstrap) } X509_free(certs[i]); } + free(certs); /* Set up CAs for OpenSSL to trust in verifying the peer's * certificate. */