Priyaranjan Nayak wrote:
      I am using openssl-1.0.1c in our project.when SSL_shutdown(ssl)
get executed it returns 0.If I get return value zero then calling  the
same SSL_shutdown(ssl) again.In 2nd time it return -1. Can any one tell
me how to shutdown ssl context ? How can I execute SSL_shutdown(ssl) ,
so that it will return 0 .

SSL_shutdown() will only return 1 when it has completed a 2 stream (send stream and receive stream) cryptographically secure shutdown.

When you call it you are only able to shutdown the 'send stream' that you control, you can not influence if or when the remote end will provide you indication of the receive stream shutdown; that is completely a software/programming matter of the implementation of the far end, not one enforced by SSL protocol specification.

It has to willingly decide to perform an SSL shutdown on its sending stream (your receiving stream), it could if it wanted keep the socket open forever, and still continue to send data (your received data) and this would not violate SSL protocol specification.


The fact that you have observed a 0 return value from SSL_shutdown() means that your end (the local end) has done everything it can and you wait for network and remote end to comply with your decision to shutdown.

If you are seeing a 0 return value, then a -1, then you have -1/WANT_READ condition see below.

If you treat the -1 return value you see like other OpenSSL API calls that operate on (SSL *) type, by using SSL_get_error(ssl) and confirm what value or error code is provided.



-1/SSL_ERROR_WANT_WRITE means the 'SSL close notify' packet has not been committed to the kernel. To resolve this you must ensure your BIO layer and below flush their data downwards when they can. You might not be able to flush data down if there is flow control in force blocking this scenario. For example write() system call returns -1/EAGAIN because the network socket write buffer is full.

If you see -1/SSL_ERROR_WANT_WRITE then your local end still has work to do, to wait for flow control to clear to allow you to commit data to the kernel and then flush your outstanding data (this data is buffered internally in OpenSSL) to kernel.



If you see SSL_shutdown(ssl) == 0, then you can call shutdown(fd, SHUT_WR) on the socket if you wish. Because the SSL protocol stack never needs to write(fd, ...) any data in the future with that socket.
NOTE: this comment presumes you are using a direct socket BIO layer.



-1/SSL_ERROR_WANT_READ means that the SSL_shutdown() API is waiting for the remote end to send its 'SSL close notify' packet. As stated above you have no control over when or if the remote end does this.

The -1/SSL_ERROR_WANT_READ is the generic 'waiting for more data' error code you get from non-blocking SSL_read() API and it has exactly the same meaning in respect of SSL shutdown, since we are waiting for data from the remote end to complete the shutdown of both streams (send and receive).

The other end does not have to send the 'SSL shutdown notify' packet and a lot of 'other ends' simply disconnect/close socket on receiving the 'SSL close notify' you sent.

If you care about a cryptographically secure shutdown you need to fix the software at the 'other end' to ensure it:
 * notices it receives a secure shutdown from the remote end
 * finishes up whatever it maybe in the middle of doing, like sending data
 * makes a decision to comply with the shutdown scenario
 * sends its 'SSL close notify' packet,
 * ensure it flushed the packet to the kernel and over the network, and
* keeps the socket open waiting for you to be the first mover in closing the socket. However SO_LINGER may help and maybe you need an application level timer for really bad software that fails to close(). * as a short-circuit the 'other end' can close() if it can ask the kernel if all pending data has been ACKed on the wire. Such as the value of the TCP SendQ in the kernel is now at a 0 value.

In reality the above never happens, unless you have some kind of high security environment since doing all that requires understanding, additional work and lowers performances (a host will have more sockets open longer).

In reality implementations are more a best-effort to be correct, rather than assured of being correct.

If you can not control or fix the other software and your application may choose not to consider this an error condition, but more a 'we did our best to be correct here, but the ignorant other end software was not such a good SSL citizen as we are, since it did not provide us with the SSL close notify packet we expected before it abruptly cause a TCP disconnection of the stream'.

Many applications do not require a cryptographic secure end-of-stream indication due to the way the application protocol works. For example HTTP/1.1 which is a request/response protocol where the client is in charge of what the responses the server provides, so if the client sends an SSL shutdown after it has received the length information of the response but maybe not all the data, then some might consider there is no need for the HTTP server to send a 'SSL close notify' packet to signal end-of-stream. It can flush all the application data of the last response being processed, check it is acked over the network, then close the socket. So to get better SSL performance metrics you might skip that in your HTTP server implementation, as it saves a few extra bytes and potentially kernel I/O system calls.



Also note some older versions SSL/TLS related protocols might not support SSL shutdown at all that impact OpenSSL API return values.



You can check SSL_get_shutdown() to see the what the SSL shutdown status is.

If it were possible to re-write the OpenSSL API, SSL_shutdown() should probably return the same value as SSL_get_shutdown().

But the 0 and 1 return value of SSL_shutdown() have been set in stone a long time ago to change.



I hope this provides a little background and understanding to what is going on.


Darryl

______________________________________________________________________
OpenSSL Project                                 http://www.openssl.org
User Support Mailing List                    openssl-users@openssl.org
Automated List Manager                           majord...@openssl.org

Reply via email to