diff --git a/examples/client/client.c b/examples/client/client.c index 5755e022d..66db505a8 100644 --- a/examples/client/client.c +++ b/examples/client/client.c @@ -209,6 +209,7 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) int nonBlocking = 0; int resumeSession = 0; int shutdown = 0; + int ret; int scr = 0; /* allow secure renegotiation */ int forceScr = 0; /* force client initiaed scr */ int trackMemory = 0; @@ -649,13 +650,7 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) if (wolfSSL_connect(ssl) != SSL_SUCCESS) err_sys("SSL_connect failed"); - if (shutdown) { /* bidirectional shutdown if true */ - if (!wolfSSL_shutdown(ssl)) - wolfSSL_shutdown(ssl); - } - else { - wolfSSL_shutdown(ssl); - } + wolfSSL_shutdown(ssl); wolfSSL_free(ssl); CloseSocket(sockfd); } @@ -815,13 +810,9 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) #endif if (doDTLS == 0) { /* don't send alert after "break" command */ - if (shutdown) { /* bidirectional shutdown if true */ - if (!wolfSSL_shutdown(ssl)) /* echoserver interprets as new conn */ - wolfSSL_shutdown(ssl); - } - else { - wolfSSL_shutdown(ssl); - } + ret = wolfSSL_shutdown(ssl); + if (shutdown && ret == SSL_SHUTDOWN_NOT_DONE) + wolfSSL_shutdown(ssl); /* bidirectional shutdown */ } #ifdef ATOMIC_USER if (atomicUser) @@ -898,13 +889,10 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args) /* try to send session break */ wolfSSL_write(sslResume, msg, msgSz); - if (shutdown) { /* bidirectional shutdown if true */ - if (!wolfSSL_shutdown(sslResume)) - wolfSSL_shutdown(sslResume); - } - else { - wolfSSL_shutdown(sslResume); - } + ret = wolfSSL_shutdown(sslResume); + if (shutdown && ret == SSL_SHUTDOWN_NOT_DONE) + wolfSSL_shutdown(sslResume); /* bidirectional shutdown */ + wolfSSL_free(sslResume); CloseSocket(sockfd); } diff --git a/examples/server/server.c b/examples/server/server.c index a2c5d0176..64a989d65 100644 --- a/examples/server/server.c +++ b/examples/server/server.c @@ -135,7 +135,7 @@ static void Usage(void) printf("-r Create server ready file, for external monitor\n"); printf("-N Use Non-blocking sockets\n"); printf("-S Use Host Name Indication\n"); - printf("-w Wait for bidirectional shutdown\n"); + printf("-w Wait for bidirectional shutdown\n"); #ifdef HAVE_OCSP printf("-o Perform OCSP lookup on peer certificate\n"); printf("-O Perform OCSP lookup using as responder\n"); @@ -175,6 +175,7 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) int pkCallbacks = 0; int serverReadyFile = 0; int shutdown = 0; + int ret; char* cipherList = NULL; const char* verifyCert = cliCert; const char* ourCert = svrCert; @@ -566,13 +567,9 @@ THREAD_RETURN CYASSL_THREAD server_test(void* args) Task_yield(); #endif - if (shutdown) { /* bidirectional shutdown if true */ - if (!SSL_shutdown(ssl)) - SSL_shutdown(ssl); - } - else { - SSL_shutdown(ssl); - } + ret = SSL_shutdown(ssl); + if (shutdown && ret == SSL_SHUTDOWN_NOT_DONE) + SSL_shutdown(ssl); /* bidirectional shutdown */ SSL_free(ssl); SSL_CTX_free(ctx); diff --git a/src/ssl.c b/src/ssl.c index 5025eab84..5ef43fc8f 100644 --- a/src/ssl.c +++ b/src/ssl.c @@ -917,6 +917,7 @@ int wolfSSL_recv(WOLFSSL* ssl, void* data, int sz, int flags) /* SSL_SUCCESS on ok */ int wolfSSL_shutdown(WOLFSSL* ssl) { + int ret = SSL_FATAL_ERROR; byte tmp; WOLFSSL_ENTER("SSL_shutdown()"); @@ -937,27 +938,30 @@ int wolfSSL_shutdown(WOLFSSL* ssl) return SSL_FATAL_ERROR; } ssl->options.sentNotify = 1; /* don't send close_notify twice */ - WOLFSSL_LEAVE("SSL_shutdown()", ssl->error); - if (ssl->options.closeNotify) - return 1; + ret = SSL_SUCCESS; else - return 0; + ret = SSL_SHUTDOWN_NOT_DONE; + + WOLFSSL_LEAVE("SSL_shutdown()", ret); + return ret; } /* call wolfSSL_shutdown again for bidirectional shudown */ if (ssl->options.sentNotify && !ssl->options.closeNotify) { - ssl->error = wolfSSL_read(ssl, &tmp, 0); - if (ssl->error < 0) { + ret = wolfSSL_read(ssl, &tmp, 0); + if (ret < 0) { WOLFSSL_ERROR(ssl->error); - return SSL_FATAL_ERROR; + ret = SSL_FATAL_ERROR; + } else if (ssl->options.closeNotify) { + ssl->error = SSL_ERROR_SYSCALL; /* simulate OpenSSL behavior */ + ret = SSL_SUCCESS; } - WOLFSSL_LEAVE("SSL_shutdown()", ssl->error); - ssl->error = SSL_ERROR_SYSCALL; /* simulate OpenSSL behavior */ - if(ssl->options.closeNotify) - return SSL_SUCCESS; } - return SSL_FATAL_ERROR; + + WOLFSSL_LEAVE("SSL_shutdown()", ret); + + return ret; } diff --git a/wolfssl/ssl.h b/wolfssl/ssl.h index 4385a15a0..721d33272 100644 --- a/wolfssl/ssl.h +++ b/wolfssl/ssl.h @@ -644,6 +644,7 @@ enum { /* ssl Constants */ SSL_ERROR_NONE = 0, /* for most functions */ SSL_FAILURE = 0, /* for some functions */ SSL_SUCCESS = 1, + SSL_SHUTDOWN_NOT_DONE = 2, /* call wolfSSL_shutdown again to complete */ SSL_BAD_CERTTYPE = -8, SSL_BAD_STAT = -7,