aboutsummaryrefslogtreecommitdiffstats
path: root/lib/ssl
diff options
context:
space:
mode:
authorIngela Anderton Andin <[email protected]>2017-03-16 16:53:50 +0100
committerIngela Anderton Andin <[email protected]>2017-03-27 14:50:52 +0200
commit8b10920bd6b41cb2a3d12a23e3edd9457d0ab102 (patch)
treeca1dcc4cc98e8a153b11b09a56dbbd7eb52dae23 /lib/ssl
parenta748cafdc7063d9f181ba12088db6458793ced2f (diff)
downloadotp-8b10920bd6b41cb2a3d12a23e3edd9457d0ab102.tar.gz
otp-8b10920bd6b41cb2a3d12a23e3edd9457d0ab102.tar.bz2
otp-8b10920bd6b41cb2a3d12a23e3edd9457d0ab102.zip
ssl: Avoid data loss in active once
Emulate active once in such a way that data recived by the TLS connection process, but not fetch via active once option by the user, can be delivered at next active once before final close.
Diffstat (limited to 'lib/ssl')
-rw-r--r--lib/ssl/src/tls_connection.erl37
1 files changed, 25 insertions, 12 deletions
diff --git a/lib/ssl/src/tls_connection.erl b/lib/ssl/src/tls_connection.erl
index e06b2fcbd5..831bbefc59 100644
--- a/lib/ssl/src/tls_connection.erl
+++ b/lib/ssl/src/tls_connection.erl
@@ -397,23 +397,36 @@ handle_info({Protocol, _, Data}, StateName,
end;
handle_info({CloseTag, Socket}, StateName,
#state{socket = Socket, close_tag = CloseTag,
+ socket_options = #socket_options{active = Active},
+ protocol_buffers = #protocol_buffers{tls_cipher_texts = CTs},
negotiated_version = Version} = State) ->
+
%% Note that as of TLS 1.1,
%% failure to properly close a connection no longer requires that a
%% session not be resumed. This is a change from TLS 1.0 to conform
%% with widespread implementation practice.
- case Version of
- {1, N} when N >= 1 ->
- ok;
- _ ->
- %% As invalidate_sessions here causes performance issues,
- %% we will conform to the widespread implementation
- %% practice and go aginst the spec
- %%invalidate_session(Role, Host, Port, Session)
- ok
- end,
- ssl_connection:handle_normal_shutdown(?ALERT_REC(?FATAL, ?CLOSE_NOTIFY), StateName, State),
- {stop, {shutdown, transport_closed}};
+
+ case (Active == false) andalso (CTs =/= []) of
+ false ->
+ case Version of
+ {1, N} when N >= 1 ->
+ ok;
+ _ ->
+ %% As invalidate_sessions here causes performance issues,
+ %% we will conform to the widespread implementation
+ %% practice and go aginst the spec
+ %%invalidate_session(Role, Host, Port, Session)
+ ok
+ end,
+
+ ssl_connection:handle_normal_shutdown(?ALERT_REC(?FATAL, ?CLOSE_NOTIFY), StateName, State),
+ {stop, {shutdown, transport_closed}};
+ true ->
+ %% Fixes non-delivery of final TLS record in {active, once}.
+ %% Basically allows the application the opportunity to set {active, once} again
+ %% and then receive the final message.
+ next_event(StateName, no_record, State)
+ end;
handle_info(Msg, StateName, State) ->
ssl_connection:handle_info(Msg, StateName, State).