diff options
Diffstat (limited to 'lib/ssl')
31 files changed, 930 insertions, 495 deletions
diff --git a/lib/ssl/doc/src/book.xml b/lib/ssl/doc/src/book.xml index 85d6b56b26..ecfb915b44 100644 --- a/lib/ssl/doc/src/book.xml +++ b/lib/ssl/doc/src/book.xml @@ -4,7 +4,7 @@ <book xmlns:xi="http://www.w3.org/2001/XInclude"> <header titlestyle="normal"> <copyright> - <year>1999</year><year>2009</year> + <year>1999</year><year>2011</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/ssl/doc/src/notes.xml b/lib/ssl/doc/src/notes.xml index 8f81ccb567..52ee9c086a 100644 --- a/lib/ssl/doc/src/notes.xml +++ b/lib/ssl/doc/src/notes.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>1999</year><year>2010</year> + <year>1999</year><year>2011</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> @@ -31,7 +31,34 @@ <p>This document describes the changes made to the SSL application. </p> - <section><title>SSL 4.1.3</title> + <section><title>SSL 4.1.4</title> + + <section><title>Improvements and New Features</title> + <list> + <item> + <p> + Reduced memory footprint of an ssl connection.</p> + <p> + Handshake hashes, premaster secret and "public_key_info" + does not need to be saved when the connection has been + established. The own certificate is no longer duplicated + in the state.</p> + <p> + Own Id: OTP-9021</p> + </item> + <item> + <p> + Add the option {hibernate_after, int()} to ssl:connect + and ssl:listen</p> + <p> + Own Id: OTP-9106</p> + </item> + </list> + </section> + +</section> + +<section><title>SSL 4.1.3</title> <section><title>Fixed Bugs and Malfunctions</title> <list> diff --git a/lib/ssl/doc/src/ssl.xml b/lib/ssl/doc/src/ssl.xml index daf7b77527..cd5c9281cd 100644 --- a/lib/ssl/doc/src/ssl.xml +++ b/lib/ssl/doc/src/ssl.xml @@ -269,6 +269,13 @@ fun(OtpCert :: #'OTPCertificate'{}, Event :: {bad_cert, Reason :: atom()} | <p> {bad_cert, cert_expired}, {bad_cert, invalid_issuer}, {bad_cert, invalid_signature}, {bad_cert, unknown_ca}, {bad_cert, name_not_permitted}, {bad_cert, missing_basic_constraint}, {bad_cert, invalid_key_usage}</p> </item> + <tag>{hibernate_after, integer()|undefined}</tag> + <item>When an integer-value is specified, the <code>ssl_connection</code> + will go into hibernation after the specified number of milliseconds + of inactivity, thus reducing its memory footprint. When + <code>undefined</code> is specified (this is the default), the process + will never go into hibernation. + </item> </taglist> </section> diff --git a/lib/ssl/doc/src/using_ssl.xml b/lib/ssl/doc/src/using_ssl.xml index 4bdd8f97b4..605290b6f9 100644 --- a/lib/ssl/doc/src/using_ssl.xml +++ b/lib/ssl/doc/src/using_ssl.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2003</year><year>2009</year> + <year>2003</year><year>2011</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/ssl/src/inet_ssl_dist.erl b/lib/ssl/src/inet_ssl_dist.erl index f62aefd35a..6c0fbc0618 100644 --- a/lib/ssl/src/inet_ssl_dist.erl +++ b/lib/ssl/src/inet_ssl_dist.erl @@ -1,8 +1,8 @@ -%%<copyright> -%% <year>2000-2008</year> -%% <holder>Ericsson AB, All Rights Reserved</holder> -%%</copyright> -%%<legalnotice> +%% +%% %CopyrightBegin% +%% +%% Copyright Ericsson AB 2000-2011. All Rights Reserved. +%% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in %% compliance with the License. You should have received a copy of the @@ -14,8 +14,9 @@ %% the License for the specific language governing rights and limitations %% under the License. %% -%% The Initial Developer of the Original Code is Ericsson AB. -%%</legalnotice> +%% %CopyrightEnd% +%% + %% -module(inet_ssl_dist). @@ -135,6 +136,9 @@ accept_connection(AcceptPid, Socket, MyNode, Allowed, SetupTime) -> [self(), AcceptPid, Socket, MyNode, Allowed, SetupTime]). +%% Suppress dialyzer warning, we do not really care about old ssl code +%% as we intend to remove it. +-spec(do_accept(_,_,_,_,_,_) -> no_return()). do_accept(Kernel, AcceptPid, Socket, MyNode, Allowed, SetupTime) -> process_flag(priority, max), receive @@ -167,8 +171,8 @@ do_accept(Kernel, AcceptPid, Socket, MyNode, Allowed, SetupTime) -> ssl_prim:getll(S) end, f_address = fun get_remote_id/2, - mf_tick = {?MODULE, tick}, - mf_getstat = {?MODULE,getstat} + mf_tick = fun ?MODULE:tick/1, + mf_getstat = fun ?MODULE:getstat/1 }, dist_util:handshake_other_started(HSData); {false,IP} -> @@ -204,6 +208,9 @@ setup(Node, Type, MyNode, LongOrShortNames,SetupTime) -> LongOrShortNames, SetupTime]). +%% Suppress dialyzer warning, we do not really care about old ssl code +%% as we intend to remove it. +-spec(do_setup(_,_,_,_,_,_) -> no_return()). do_setup(Kernel, Node, Type, MyNode, LongOrShortNames,SetupTime) -> process_flag(priority, max), ?trace("~p~n",[{inet_ssl_dist,self(),setup,Node}]), @@ -258,8 +265,8 @@ do_setup(Kernel, Node, Type, MyNode, LongOrShortNames,SetupTime) -> protocol = ssl, family = inet} end, - mf_tick = {?MODULE, tick}, - mf_getstat = {?MODULE,getstat}, + mf_tick = fun ?MODULE:tick/1, + mf_getstat = fun ?MODULE:getstat/1, request_type = Type }, dist_util:handshake_we_started(HSData); diff --git a/lib/ssl/src/ssl.appup.src b/lib/ssl/src/ssl.appup.src index e6a8c557fc..d3e426f254 100644 --- a/lib/ssl/src/ssl.appup.src +++ b/lib/ssl/src/ssl.appup.src @@ -1,12 +1,14 @@ %% -*- erlang -*- {"%VSN%", [ + {"4.1.3", [{restart_application, ssl}]}, {"4.1.2", [{restart_application, ssl}]}, {"4.1.1", [{restart_application, ssl}]}, {"4.1", [{restart_application, ssl}]}, {"4.0.1", [{restart_application, ssl}]} ], [ + {"4.1.3", [{restart_application, ssl}]}, {"4.1.2", [{restart_application, ssl}]}, {"4.1.1", [{restart_application, ssl}]}, {"4.1", [{restart_application, ssl}]}, diff --git a/lib/ssl/src/ssl.erl b/lib/ssl/src/ssl.erl index 0e108c430f..7b1fda4cf9 100644 --- a/lib/ssl/src/ssl.erl +++ b/lib/ssl/src/ssl.erl @@ -52,15 +52,14 @@ -type option() :: socketoption() | ssloption() | transportoption(). -type socketoption() :: [{property(), term()}]. %% See gen_tcp and inet -type property() :: atom(). - -type ssloption() :: {verify, verify_type()} | {verify_fun, {fun(), InitialUserState::term()}} | {fail_if_no_peer_cert, boolean()} | {depth, integer()} | - {cert, der_encoded()} | {certfile, path()} | {key, der_encoded()} | - {keyfile, path()} | {password, string()} | {cacerts, [der_encoded()]} | - {cacertfile, path()} | {dh, der_encoded()} | {dhfile, path()} | + {cert, Der::binary()} | {certfile, path()} | {key, Der::binary()} | + {keyfile, path()} | {password, string()} | {cacerts, [Der::binary()]} | + {cacertfile, path()} | {dh, Der::binary()} | {dhfile, path()} | {ciphers, ciphers()} | {ssl_imp, ssl_imp()} | {reuse_sessions, boolean()} | - {reuse_session, fun()}. + {reuse_session, fun()} | {hibernate_after, integer()|undefined}. -type verify_type() :: verify_none | verify_peer. -type path() :: string(). @@ -72,8 +71,8 @@ %%-------------------------------------------------------------------- --spec start() -> ok. --spec start(permanent | transient | temporary) -> ok. +-spec start() -> ok | {error, reason()}. +-spec start(permanent | transient | temporary) -> ok | {error, reason()}. %% %% Description: Utility function that starts the ssl, %% crypto and public_key applications. Default type @@ -98,9 +97,12 @@ stop() -> application:stop(ssl). %%-------------------------------------------------------------------- --spec connect(host() | port(), [option()]) -> {ok, #sslsocket{}}. --spec connect(host() | port(), [option()] | port_num(), timeout() | list()) -> {ok, #sslsocket{}}. --spec connect(host() | port(), port_num(), list(), timeout()) -> {ok, #sslsocket{}}. +-spec connect(host() | port(), [option()]) -> {ok, #sslsocket{}} | + {error, reason()}. +-spec connect(host() | port(), [option()] | port_num(), timeout() | list()) -> + {ok, #sslsocket{}} | {error, reason()}. +-spec connect(host() | port(), port_num(), list(), timeout()) -> + {ok, #sslsocket{}} | {error, reason()}. %% %% Description: Connect to a ssl server. @@ -171,8 +173,10 @@ listen(Port, Options0) -> end. %%-------------------------------------------------------------------- --spec transport_accept(#sslsocket{}) -> {ok, #sslsocket{}}. --spec transport_accept(#sslsocket{}, timeout()) -> {ok, #sslsocket{}}. +-spec transport_accept(#sslsocket{}) -> {ok, #sslsocket{}} | + {error, reason()}. +-spec transport_accept(#sslsocket{}, timeout()) -> {ok, #sslsocket{}} | + {error, reason()}. %% %% Description: Performs transport accept on a ssl listen socket %%-------------------------------------------------------------------- @@ -706,7 +710,8 @@ handle_options(Opts0, _Role) -> reuse_sessions = handle_option(reuse_sessions, Opts, true), secure_renegotiate = handle_option(secure_renegotiate, Opts, false), renegotiate_at = handle_option(renegotiate_at, Opts, ?DEFAULT_RENEGOTIATE_AT), - debug = handle_option(debug, Opts, []) + debug = handle_option(debug, Opts, []), + hibernate_after = handle_option(hibernate_after, Opts, undefined) }, CbInfo = proplists:get_value(cb_info, Opts, {gen_tcp, tcp, tcp_closed, tcp_error}), @@ -715,7 +720,7 @@ handle_options(Opts0, _Role) -> depth, cert, certfile, key, keyfile, password, cacerts, cacertfile, dh, dhfile, ciphers, debug, reuse_session, reuse_sessions, ssl_imp, - cb_info, renegotiate_at, secure_renegotiate], + cb_info, renegotiate_at, secure_renegotiate, hibernate_after], SockOpts = lists:foldl(fun(Key, PropList) -> proplists:delete(Key, PropList) @@ -822,6 +827,10 @@ validate_option(renegotiate_at, Value) when is_integer(Value) -> validate_option(debug, Value) when is_list(Value); Value == true -> Value; +validate_option(hibernate_after, undefined) -> + undefined; +validate_option(hibernate_after, Value) when is_integer(Value), Value >= 0 -> + Value; validate_option(Opt, Value) -> throw({error, {eoptions, {Opt, Value}}}). diff --git a/lib/ssl/src/ssl_app.erl b/lib/ssl/src/ssl_app.erl index 8d50fd7bdb..c9f81726b9 100644 --- a/lib/ssl/src/ssl_app.erl +++ b/lib/ssl/src/ssl_app.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1998-2009. All Rights Reserved. +%% Copyright Ericsson AB 1998-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in diff --git a/lib/ssl/src/ssl_connection.erl b/lib/ssl/src/ssl_connection.erl index 489895cf29..574e1e9468 100644 --- a/lib/ssl/src/ssl_connection.erl +++ b/lib/ssl/src/ssl_connection.erl @@ -289,9 +289,9 @@ start_link(Role, Host, Port, Socket, Options, User, CbInfo) -> %% gen_fsm callbacks %%==================================================================== %%-------------------------------------------------------------------- --spec init(list()) -> {ok, state_name(), #state{}} | {stop, term()}. +-spec init(list()) -> {ok, state_name(), #state{}, timeout()} | {stop, term()}. %% Possible return values not used now. -%% | {ok, state_name(), #state{}, timeout()} | +%% | {ok, state_name(), #state{}} | %% ignore %% Description:Whenever a gen_fsm is started using gen_fsm:start/[3,4] or %% gen_fsm:start_link/3,4, this function is called by the new process to @@ -311,7 +311,7 @@ init([Role, Host, Port, Socket, {SSLOpts0, _} = Options, session_cache = CacheRef, private_key = Key, diffie_hellman_params = DHParams}, - {ok, hello, State} + {ok, hello, State, get_timeout(State)} catch throw:Error -> {stop, Error} @@ -412,6 +412,9 @@ hello(Hello = #client_hello{client_version = ClientVersion}, {stop, normal, State} end; +hello(timeout, State) -> + { next_state, hello, State, hibernate }; + hello(Msg, State) -> handle_unexpected_message(Msg, hello, State). %%-------------------------------------------------------------------- @@ -460,6 +463,9 @@ abbreviated(#finished{verify_data = Data} = Finished, {stop, normal, State} end; +abbreviated(timeout, State) -> + { next_state, abbreviated, State, hibernate }; + abbreviated(Msg, State) -> handle_unexpected_message(Msg, abbreviated, State). @@ -582,6 +588,9 @@ certify(#client_key_exchange{exchange_keys = Keys}, {stop, normal, State} end; +certify(timeout, State) -> + { next_state, certify, State, hibernate }; + certify(Msg, State) -> handle_unexpected_message(Msg, certify, State). @@ -664,6 +673,9 @@ cipher(#finished{verify_data = Data} = Finished, {stop, normal, State} end; +cipher(timeout, State) -> + { next_state, cipher, State, hibernate }; + cipher(Msg, State) -> handle_unexpected_message(Msg, cipher, State). @@ -693,6 +705,9 @@ connection(#hello_request{}, #state{host = Host, port = Port, connection(#client_hello{} = Hello, #state{role = server} = State) -> hello(Hello, State); +connection(timeout, State) -> + {next_state, connection, State, hibernate}; + connection(Msg, State) -> handle_unexpected_message(Msg, connection, State). %%-------------------------------------------------------------------- @@ -705,7 +720,7 @@ connection(Msg, State) -> %% the event. Not currently used! %%-------------------------------------------------------------------- handle_event(_Event, StateName, State) -> - {next_state, StateName, State}. + {next_state, StateName, State, get_timeout(State)}. %%-------------------------------------------------------------------- -spec handle_sync_event(term(), from(), state_name(), #state{}) -> @@ -736,7 +751,8 @@ handle_sync_event({application_data, Data0}, From, connection, {Msgs, [], ConnectionStates} -> Result = Transport:send(Socket, Msgs), {reply, Result, - connection, State#state{connection_states = ConnectionStates}}; + connection, State#state{connection_states = ConnectionStates}, + get_timeout(State)}; {Msgs, RestData, ConnectionStates} -> if Msgs =/= [] -> @@ -749,12 +765,14 @@ handle_sync_event({application_data, Data0}, From, connection, renegotiation = {true, internal}}) end catch throw:Error -> - {reply, Error, connection, State} + {reply, Error, connection, State, get_timeout(State)} end; handle_sync_event({application_data, Data}, From, StateName, #state{send_queue = Queue} = State) -> %% In renegotiation priorities handshake, send data when handshake is finished - {next_state, StateName, State#state{send_queue = queue:in({From, Data}, Queue)}}; + {next_state, StateName, + State#state{send_queue = queue:in({From, Data}, Queue)}, + get_timeout(State)}; handle_sync_event(start, From, hello, State) -> hello(start, State#state{from = From}); @@ -768,9 +786,9 @@ handle_sync_event(start, From, hello, State) -> %% here to make sure it is the users problem and not owers if %% they upgrade a active socket. handle_sync_event(start, _, connection, State) -> - {reply, connected, connection, State}; + {reply, connected, connection, State, get_timeout(State)}; handle_sync_event(start, From, StateName, State) -> - {next_state, StateName, State#state{from = From}}; + {next_state, StateName, State#state{from = From}, get_timeout(State)}; handle_sync_event(close, _, StateName, State) -> %% Run terminate before returning @@ -796,7 +814,7 @@ handle_sync_event({shutdown, How0}, _, StateName, case Transport:shutdown(Socket, How0) of ok -> - {reply, ok, StateName, State}; + {reply, ok, StateName, State, get_timeout(State)}; Error -> {stop, normal, Error, State} end; @@ -807,30 +825,33 @@ handle_sync_event({recv, N}, From, connection = StateName, State0) -> %% Doing renegotiate wait with handling request until renegotiate is %% finished. Will be handled by next_state_connection/2. handle_sync_event({recv, N}, From, StateName, State) -> - {next_state, StateName, State#state{bytes_to_read = N, from = From, - recv_during_renegotiation = true}}; + {next_state, StateName, + State#state{bytes_to_read = N, from = From, + recv_during_renegotiation = true}, + get_timeout(State)}; handle_sync_event({new_user, User}, _From, StateName, State =#state{user_application = {OldMon, _}}) -> NewMon = erlang:monitor(process, User), erlang:demonitor(OldMon, [flush]), - {reply, ok, StateName, State#state{user_application = {NewMon,User}}}; + {reply, ok, StateName, State#state{user_application = {NewMon,User}}, + get_timeout(State)}; handle_sync_event({get_opts, OptTags}, _From, StateName, #state{socket = Socket, socket_options = SockOpts} = State) -> OptsReply = get_socket_opts(Socket, OptTags, SockOpts, []), - {reply, OptsReply, StateName, State}; + {reply, OptsReply, StateName, State, get_timeout(State)}; handle_sync_event(sockname, _From, StateName, #state{socket = Socket} = State) -> SockNameReply = inet:sockname(Socket), - {reply, SockNameReply, StateName, State}; + {reply, SockNameReply, StateName, State, get_timeout(State)}; handle_sync_event(peername, _From, StateName, #state{socket = Socket} = State) -> PeerNameReply = inet:peername(Socket), - {reply, PeerNameReply, StateName, State}; + {reply, PeerNameReply, StateName, State, get_timeout(State)}; handle_sync_event({set_opts, Opts0}, _From, StateName, #state{socket_options = Opts1, @@ -840,27 +861,27 @@ handle_sync_event({set_opts, Opts0}, _From, StateName, State1 = State0#state{socket_options = Opts}, if Opts#socket_options.active =:= false -> - {reply, ok, StateName, State1}; + {reply, ok, StateName, State1, get_timeout(State1)}; Buffer =:= <<>>, Opts1#socket_options.active =:= false -> %% Need data, set active once {Record, State2} = next_record_if_active(State1), case next_state(StateName, Record, State2) of - {next_state, StateName, State} -> - {reply, ok, StateName, State}; + {next_state, StateName, State, Timeout} -> + {reply, ok, StateName, State, Timeout}; {stop, Reason, State} -> {stop, Reason, State} end; Buffer =:= <<>> -> %% Active once already set - {reply, ok, StateName, State1}; + {reply, ok, StateName, State1, get_timeout(State1)}; true -> case application_data(<<>>, State1) of Stop = {stop,_,_} -> Stop; {Record, State2} -> case next_state(StateName, Record, State2) of - {next_state, StateName, State} -> - {reply, ok, StateName, State}; + {next_state, StateName, State, Timeout} -> + {reply, ok, StateName, State, Timeout}; {stop, Reason, State} -> {stop, Reason, State} end @@ -871,7 +892,7 @@ handle_sync_event(renegotiate, From, connection, State) -> renegotiate(State#state{renegotiation = {true, From}}); handle_sync_event(renegotiate, _, StateName, State) -> - {reply, {error, already_renegotiating}, StateName, State}; + {reply, {error, already_renegotiating}, StateName, State, get_timeout(State)}; handle_sync_event(info, _, StateName, #state{negotiated_version = Version, @@ -879,19 +900,19 @@ handle_sync_event(info, _, StateName, AtomVersion = ssl_record:protocol_version(Version), {reply, {ok, {AtomVersion, ssl_cipher:suite_definition(Suite)}}, - StateName, State}; + StateName, State, get_timeout(State)}; handle_sync_event(session_info, _, StateName, #state{session = #session{session_id = Id, cipher_suite = Suite}} = State) -> {reply, [{session_id, Id}, {cipher_suite, ssl_cipher:suite_definition(Suite)}], - StateName, State}; + StateName, State, get_timeout(State)}; handle_sync_event(peer_certificate, _, StateName, #state{session = #session{peer_certificate = Cert}} = State) -> - {reply, {ok, Cert}, StateName, State}. + {reply, {ok, Cert}, StateName, State, get_timeout(State)}. %%-------------------------------------------------------------------- -spec handle_info(msg(),state_name(), #state{}) -> @@ -955,7 +976,7 @@ handle_info({'DOWN', MonitorRef, _, _, _}, _, handle_info(Msg, StateName, State) -> Report = io_lib:format("SSL: Got unexpected info: ~p ~n", [Msg]), error_logger:info_report(Report), - {next_state, StateName, State}. + {next_state, StateName, State, get_timeout(State)}. %%-------------------------------------------------------------------- -spec terminate(reason(), state_name(), #state{}) -> term(). @@ -1086,13 +1107,13 @@ init_private_key({rsa, PrivateKey}, _, _,_) -> init_private_key({dsa, PrivateKey},_,_,_) -> public_key:der_decode('DSAPrivateKey', PrivateKey). --spec(handle_file_error/6 :: (_,_,_,_,_,_) -> no_return()). +-spec(handle_file_error(_,_,_,_,_,_) -> no_return()). handle_file_error(Line, Error, {badmatch, Reason}, File, Throw, Stack) -> file_error(Line, Error, Reason, File, Throw, Stack); handle_file_error(Line, Error, Reason, File, Throw, Stack) -> file_error(Line, Error, Reason, File, Throw, Stack). --spec(file_error/6 :: (_,_,_,_,_,_) -> no_return()). +-spec(file_error(_,_,_,_,_,_) -> no_return()). file_error(Line, Error, Reason, File, Throw, Stack) -> Report = io_lib:format("SSL: ~p: ~p:~p ~s~n ~p~n", [Line, Error, Reason, File, Stack]), @@ -1412,8 +1433,6 @@ key_exchange(#state{role = client, State#state{connection_states = ConnectionStates1, tls_handshake_hashes = Hashes1}. --spec(rsa_key_exchange/2 :: (_,_) -> no_return()). - rsa_key_exchange(PremasterSecret, PublicKeyInfo = {Algorithm, _, _}) when Algorithm == ?rsaEncryption; Algorithm == ?md2WithRSAEncryption; @@ -1780,7 +1799,7 @@ handle_tls_handshake(Handle, StateName, #state{tls_packets = [Packet]} = State) handle_tls_handshake(Handle, StateName, #state{tls_packets = [Packet | Packets]} = State0) -> FsmReturn = {next_state, StateName, State0#state{tls_packets = Packets}}, case Handle(Packet, FsmReturn) of - {next_state, NextStateName, State} -> + {next_state, NextStateName, State, _Timeout} -> handle_tls_handshake(Handle, NextStateName, State); {stop, _,_} = Stop -> Stop @@ -1791,11 +1810,11 @@ next_state(_, #alert{} = Alert, #state{negotiated_version = Version} = State) -> {stop, normal, State}; next_state(Next, no_record, State) -> - {next_state, Next, State}; + {next_state, Next, State, get_timeout(State)}; next_state(Next, #ssl_tls{type = ?ALERT, fragment = EncAlerts}, State) -> Alerts = decode_alerts(EncAlerts), - handle_alerts(Alerts, {next_state, Next, State}); + handle_alerts(Alerts, {next_state, Next, State, get_timeout(State)}); next_state(StateName, #ssl_tls{type = ?HANDSHAKE, fragment = Data}, State0 = #state{tls_handshake_buffer = Buf0, negotiated_version = Version}) -> @@ -2046,7 +2065,7 @@ handle_alerts([], Result) -> handle_alerts(_, {stop, _, _} = Stop) -> %% If it is a fatal alert immediately close Stop; -handle_alerts([Alert | Alerts], {next_state, StateName, State}) -> +handle_alerts([Alert | Alerts], {next_state, StateName, State, _Timeout}) -> handle_alerts(Alerts, handle_alert(Alert, StateName, State)). handle_alert(#alert{level = ?FATAL} = Alert, StateName, @@ -2227,3 +2246,8 @@ linux_workaround_transport_delivery_problems(#alert{level = ?FATAL}, Socket) -> end; linux_workaround_transport_delivery_problems(_, _) -> ok. + +get_timeout(#state{ssl_options=#ssl_options{hibernate_after=undefined}}) -> + infinity; +get_timeout(#state{ssl_options=#ssl_options{hibernate_after=HibernateAfter}}) -> + HibernateAfter. diff --git a/lib/ssl/src/ssl_handshake.hrl b/lib/ssl/src/ssl_handshake.hrl index 8ae4d2332e..fb0ebac7d1 100644 --- a/lib/ssl/src/ssl_handshake.hrl +++ b/lib/ssl/src/ssl_handshake.hrl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2007-2010. All Rights Reserved. +%% Copyright Ericsson AB 2007-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -29,9 +29,8 @@ -include_lib("public_key/include/public_key.hrl"). -type algo_oid() :: ?'rsaEncryption' | ?'id-dsa'. --type public_key() :: #'RSAPublicKey'{} | integer(). -type public_key_params() :: #'Dss-Parms'{} | term(). --type public_key_info() :: {algo_oid(), public_key(), public_key_params()}. +-type public_key_info() :: {algo_oid(), #'RSAPublicKey'{} | integer() , public_key_params()}. -record(session, { session_id, diff --git a/lib/ssl/src/ssl_internal.hrl b/lib/ssl/src/ssl_internal.hrl index 715941e3ad..c28daa271e 100644 --- a/lib/ssl/src/ssl_internal.hrl +++ b/lib/ssl/src/ssl_internal.hrl @@ -98,7 +98,11 @@ reuse_sessions, % boolean() renegotiate_at, secure_renegotiate, - debug % + debug, + hibernate_after % undefined if not hibernating, + % or number of ms of inactivity + % after which ssl_connection will + % go into hibernation }). -record(socket_options, diff --git a/lib/ssl/test/Makefile b/lib/ssl/test/Makefile index c0a7f8d257..fd3b6d06ad 100644 --- a/lib/ssl/test/Makefile +++ b/lib/ssl/test/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 1999-2010. All Rights Reserved. +# Copyright Ericsson AB 1999-2011. All Rights Reserved. # # The contents of this file are subject to the Erlang Public License, # Version 1.1, (the "License"); you may not use this file except in @@ -60,6 +60,7 @@ ERL_FILES = $(MODULES:%=%.erl) HRL_FILES = ssl_test_MACHINE.hrl HRL_FILES_SRC = \ + ssl_int.hrl \ ssl_alert.hrl \ ssl_handshake.hrl @@ -126,7 +127,7 @@ release_spec: opt release_tests_spec: opt $(INSTALL_DIR) $(RELSYSDIR) $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(HRL_FILES_NEEDED_IN_TEST) $(COVER_FILE) $(RELSYSDIR) - $(INSTALL_DATA) ssl.spec $(RELSYSDIR) + $(INSTALL_DATA) ssl.spec ssl.cover $(RELSYSDIR) chmod -f -R u+w $(RELSYSDIR) @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -) diff --git a/lib/ssl/test/make_certs.erl b/lib/ssl/test/make_certs.erl index 3c18a905b4..693289990c 100644 --- a/lib/ssl/test/make_certs.erl +++ b/lib/ssl/test/make_certs.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2007-2009. All Rights Reserved. +%% Copyright Ericsson AB 2007-2010. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in diff --git a/lib/ssl/test/old_ssl_active_SUITE.erl b/lib/ssl/test/old_ssl_active_SUITE.erl index d1cec26827..52ff0bcc5d 100644 --- a/lib/ssl/test/old_ssl_active_SUITE.erl +++ b/lib/ssl/test/old_ssl_active_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1999-2010. All Rights Reserved. +%% Copyright Ericsson AB 1999-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,11 +20,10 @@ %% -module(old_ssl_active_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, cinit_return_chkclose/1, sinit_return_chkclose/1, cinit_big_return_chkclose/1, @@ -40,7 +39,7 @@ -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). -define(MANYCONNS, ssl_test_MACHINE:many_conns()). @@ -49,33 +48,35 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of ssl.erl interface in active mode."; -all(suite) -> - {conf, - config, - [cinit_return_chkclose, - sinit_return_chkclose, - cinit_big_return_chkclose, - sinit_big_return_chkclose, - cinit_big_echo_chkclose, - cinit_huge_echo_chkclose, - sinit_big_echo_chkclose, - cinit_few_echo_chkclose, - cinit_many_echo_chkclose, - cinit_cnocert], - finish}. - -config(doc) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [cinit_return_chkclose, sinit_return_chkclose, + cinit_big_return_chkclose, sinit_big_return_chkclose, + cinit_big_echo_chkclose, cinit_huge_echo_chkclose, + sinit_big_echo_chkclose, cinit_few_echo_chkclose, + cinit_many_echo_chkclose, cinit_cnocert]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains, and record the number of available " "file descriptors"; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), case os:type() of {unix, _} -> @@ -87,20 +88,25 @@ config(Config) -> %% operating system, version of OTP, Erts, kernel and stdlib. %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto!"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. cinit_return_chkclose(doc) -> diff --git a/lib/ssl/test/old_ssl_active_once_SUITE.erl b/lib/ssl/test/old_ssl_active_once_SUITE.erl index 63eaa730e9..c7beadb301 100644 --- a/lib/ssl/test/old_ssl_active_once_SUITE.erl +++ b/lib/ssl/test/old_ssl_active_once_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2002-2010. All Rights Reserved. +%% Copyright Ericsson AB 2002-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,11 +20,10 @@ %% -module(old_ssl_active_once_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, server_accept_timeout/1, cinit_return_chkclose/1, sinit_return_chkclose/1, @@ -40,7 +39,7 @@ -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). -define(MANYCONNS, ssl_test_MACHINE:many_conns()). @@ -49,50 +48,57 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of ssl.erl interface in passive mode."; -all(suite) -> - {conf, - config, - [server_accept_timeout, - cinit_return_chkclose, - sinit_return_chkclose, - cinit_big_return_chkclose, - sinit_big_return_chkclose, - cinit_big_echo_chkclose, - cinit_huge_echo_chkclose, - sinit_big_echo_chkclose, - cinit_few_echo_chkclose, - cinit_many_echo_chkclose, - cinit_cnocert], - finish}. - -config(doc) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [server_accept_timeout, cinit_return_chkclose, + sinit_return_chkclose, cinit_big_return_chkclose, + sinit_big_return_chkclose, cinit_big_echo_chkclose, + cinit_huge_echo_chkclose, sinit_big_echo_chkclose, + cinit_few_echo_chkclose, cinit_many_echo_chkclose, + cinit_cnocert]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. server_accept_timeout(doc) -> diff --git a/lib/ssl/test/old_ssl_dist_SUITE.erl b/lib/ssl/test/old_ssl_dist_SUITE.erl index 97090c1409..4544fb616a 100644 --- a/lib/ssl/test/old_ssl_dist_SUITE.erl +++ b/lib/ssl/test/old_ssl_dist_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2007-2010. All Rights Reserved. +%% Copyright Ericsson AB 2007-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -29,39 +29,55 @@ %%%------------------------------------------------------------------- -module(old_ssl_dist_SUITE). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -define(DEFAULT_TIMETRAP_SECS, 240). -define(AWAIT_SLL_NODE_UP_TIMEOUT, 30000). --export([all/1]). +-export([all/0, suite/0,groups/0,init_per_group/2,end_per_group/2]). -export([init_per_suite/1, end_per_suite/1, init_per_testcase/2, - fin_per_testcase/2]). + end_per_testcase/2]). -export([cnct2tstsrvr/1]). -export([basic/1]). -record(node_handle, {connection_handler, socket, name, nodename}). -all(doc) -> - []; -all(suite) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> [basic]. +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + init_per_suite(Config) -> - add_ssl_opts_config(Config). + try crypto:start() of + ok -> + add_ssl_opts_config(Config) + catch _:_ -> + {skip, "Crypto did not start"} + end. end_per_suite(Config) -> + application:stop(crypto), Config. init_per_testcase(Case, Config) when list(Config) -> Dog = ?t:timetrap(?t:seconds(?DEFAULT_TIMETRAP_SECS)), [{watchdog, Dog},{testcase, Case}|Config]. -fin_per_testcase(_Case, Config) when list(Config) -> +end_per_testcase(_Case, Config) when list(Config) -> Dog = ?config(watchdog, Config), ?t:timetrap_cancel(Dog), ok. diff --git a/lib/ssl/test/old_ssl_misc_SUITE.erl b/lib/ssl/test/old_ssl_misc_SUITE.erl index 2767123a12..ea03e83867 100644 --- a/lib/ssl/test/old_ssl_misc_SUITE.erl +++ b/lib/ssl/test/old_ssl_misc_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2003-2010. All Rights Reserved. +%% Copyright Ericsson AB 2003-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,18 +20,17 @@ %% -module(old_ssl_misc_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, seed/1, app/1 ]). -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). -define(MANYCONNS, 5). @@ -40,41 +39,52 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of misc in ssl.erl interface."; -all(suite) -> - {conf, - config, - [seed, app], - finish - }. +suite() -> [{ct_hooks,[ts_install_cth]}]. -config(doc) -> +all() -> + [seed, app]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto!"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. seed(doc) -> diff --git a/lib/ssl/test/old_ssl_passive_SUITE.erl b/lib/ssl/test/old_ssl_passive_SUITE.erl index 96a7938583..7b54fe876a 100644 --- a/lib/ssl/test/old_ssl_passive_SUITE.erl +++ b/lib/ssl/test/old_ssl_passive_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1999-2010. All Rights Reserved. +%% Copyright Ericsson AB 1999-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,11 +20,10 @@ %% -module(old_ssl_passive_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, + end_per_suite/1, init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, server_accept_timeout/1, cinit_return_chkclose/1, sinit_return_chkclose/1, @@ -40,7 +39,7 @@ -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). -define(MANYCONNS, ssl_test_MACHINE:many_conns()). @@ -49,49 +48,56 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of ssl.erl interface in passive mode."; -all(suite) -> - {conf, - config, - [server_accept_timeout, - cinit_return_chkclose, - sinit_return_chkclose, - cinit_big_return_chkclose, - sinit_big_return_chkclose, - cinit_big_echo_chkclose, - sinit_big_echo_chkclose, - cinit_few_echo_chkclose, - cinit_many_echo_chkclose, - cinit_cnocert], - finish}. - -config(doc) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [server_accept_timeout, cinit_return_chkclose, + sinit_return_chkclose, cinit_big_return_chkclose, + sinit_big_return_chkclose, cinit_big_echo_chkclose, + sinit_big_echo_chkclose, cinit_few_echo_chkclose, + cinit_many_echo_chkclose, cinit_cnocert]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. server_accept_timeout(doc) -> diff --git a/lib/ssl/test/old_ssl_peer_cert_SUITE.erl b/lib/ssl/test/old_ssl_peer_cert_SUITE.erl index e5b3975d41..ee19bad175 100644 --- a/lib/ssl/test/old_ssl_peer_cert_SUITE.erl +++ b/lib/ssl/test/old_ssl_peer_cert_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2003-2010. All Rights Reserved. +%% Copyright Ericsson AB 2003-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,11 +20,10 @@ %% -module(old_ssl_peer_cert_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, cinit_plain/1, cinit_both_verify/1, cinit_cnocert/1 @@ -32,7 +31,7 @@ -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). @@ -40,42 +39,52 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of ssl verification and peer certificate retrieval."; -all(suite) -> - {conf, - config, - [cinit_plain, - cinit_both_verify, - cinit_cnocert], - finish}. - -config(doc) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [cinit_plain, cinit_both_verify, cinit_cnocert]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. cinit_plain(doc) -> diff --git a/lib/ssl/test/old_ssl_protocol_SUITE.erl b/lib/ssl/test/old_ssl_protocol_SUITE.erl index efdbf45a3d..9b9937c210 100644 --- a/lib/ssl/test/old_ssl_protocol_SUITE.erl +++ b/lib/ssl/test/old_ssl_protocol_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2005-2010. All Rights Reserved. +%% Copyright Ericsson AB 2005-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,13 +20,15 @@ %% -module(old_ssl_protocol_SUITE). --export([all/1, init_per_testcase/2, fin_per_testcase/2, config/1, - finish/1, sslv2/1, sslv3/1, tlsv1/1, sslv2_sslv3/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, + init_per_testcase/2, end_per_testcase/2, + sslv2/1, sslv3/1, tlsv1/1, sslv2_sslv3/1, sslv2_tlsv1/1, sslv3_tlsv1/1, sslv2_sslv3_tlsv1/1]). -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). @@ -34,41 +36,53 @@ init_per_testcase(_Case, Config) -> WatchDog = test_server:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of configuration protocol_version."; -all(suite) -> - {conf, - config, - [sslv2, sslv3, tlsv1, sslv2_sslv3, sslv2_tlsv1, sslv3_tlsv1, - sslv2_sslv3_tlsv1], - finish}. +suite() -> [{ct_hooks,[ts_install_cth]}]. -config(doc) -> +all() -> + [sslv2, sslv3, tlsv1, sslv2_sslv3, sslv2_tlsv1, + sslv3_tlsv1, sslv2_sslv3_tlsv1]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto"} + end. + +end_per_suite(doc) -> "This test case has no other purpose than closing the conf case."; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. %%%%% diff --git a/lib/ssl/test/old_ssl_verify_SUITE.erl b/lib/ssl/test/old_ssl_verify_SUITE.erl index 7a8cd1578a..4c11ea6850 100644 --- a/lib/ssl/test/old_ssl_verify_SUITE.erl +++ b/lib/ssl/test/old_ssl_verify_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1999-2010. All Rights Reserved. +%% Copyright Ericsson AB 1999-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -20,18 +20,17 @@ %% -module(old_ssl_verify_SUITE). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, - config/1, - finish/1, + end_per_testcase/2, cinit_both_verify/1, cinit_cnocert/1 ]). -import(ssl_test_MACHINE, [mk_ssl_cert_opts/1, test_one_listener/7, test_server_only/6]). --include("test_server.hrl"). +-include_lib("test_server/include/test_server.hrl"). -include("ssl_test_MACHINE.hrl"). @@ -39,41 +38,52 @@ init_per_testcase(_Case, Config) -> WatchDog = ssl_test_lib:timetrap(?DEFAULT_TIMEOUT), [{watchdog, WatchDog}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test of ssl.erl interface in active mode."; -all(suite) -> - {conf, - config, - [cinit_both_verify, - cinit_cnocert], - finish}. +suite() -> [{ct_hooks,[ts_install_cth]}]. -config(doc) -> +all() -> + [cinit_both_verify, cinit_cnocert]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + +init_per_suite(doc) -> "Want to se what Config contains."; -config(suite) -> +init_per_suite(suite) -> []; -config(Config) -> +init_per_suite(Config) -> io:format("Config: ~p~n", [Config]), %% Check if SSL exists. If this case fails, all other cases are skipped - crypto:start(), - application:start(public_key), - case ssl:start() of - ok -> ssl:stop(); - {error, {already_started, _}} -> ssl:stop(); - Error -> ?t:fail({failed_starting_ssl,Error}) - end, - Config. - -finish(doc) -> + case catch crypto:start() of + ok -> + application:start(public_key), + case ssl:start() of + ok -> ssl:stop(); + {error, {already_started, _}} -> ssl:stop(); + Error -> ?t:fail({failed_starting_ssl,Error}) + end, + Config; + _Else -> + {skip,"Could not start crypto"} + end. + +end_per_suite(doc) -> "This test case has no mission other than closing the conf case"; -finish(suite) -> +end_per_suite(suite) -> []; -finish(Config) -> +end_per_suite(Config) -> + crypto:stop(), Config. cinit_both_verify(doc) -> diff --git a/lib/ssl/test/old_transport_accept_SUITE.erl b/lib/ssl/test/old_transport_accept_SUITE.erl index 71c1d9e181..6f0c8e456b 100644 --- a/lib/ssl/test/old_transport_accept_SUITE.erl +++ b/lib/ssl/test/old_transport_accept_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2007-2010. All Rights Reserved. +%% Copyright Ericsson AB 2007-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -19,16 +19,17 @@ %% -module(old_transport_accept_SUITE). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -include("test_server_line.hrl"). %% Default timetrap timeout (set in init_per_testcase). -define(default_timeout, ?t:minutes(1)). -define(application, ssh). --export([all/1, +-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, + init_per_group/2,end_per_group/2, init_per_testcase/2, - fin_per_testcase/2, + end_per_testcase/2, config/1, echo_once/1, echo_twice/1, @@ -43,15 +44,37 @@ init_per_testcase(_Case, Config) -> [{watchdog, WatchDog}, {protomod, gen_tcp}, {serialize_accept, true}| Config]. -fin_per_testcase(_Case, Config) -> +end_per_testcase(_Case, Config) -> WatchDog = ?config(watchdog, Config), test_server:timetrap_cancel(WatchDog). -all(doc) -> - "Test transport_accept and ssl_accept"; -all(suite) -> +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> [config, echo_once, echo_twice, close_before_ssl_accept]. +groups() -> + []. + +init_per_suite(Config) -> + try crypto:start() of + ok -> + Config + catch _:_ -> + {skip, "Crypto did not start"} + end. + +end_per_suite(_Config) -> + application:stop(crypto), + ok. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + + config(doc) -> "Want to se what Config contains."; config(suite) -> diff --git a/lib/ssl/test/ssl.cover b/lib/ssl/test/ssl.cover index e8daa363c5..60774cc0f1 100644 --- a/lib/ssl/test/ssl.cover +++ b/lib/ssl/test/ssl.cover @@ -1,19 +1,21 @@ -{exclude, [ssl_pkix_oid, - 'PKIX1Algorithms88', - 'PKIX1Explicit88', - 'PKIX1Implicit88', - 'PKIXAttributeCertificate', - 'SSL-PKIX', - ssl_pem, - ssl_pkix, - ssl_base64, - ssl_broker, - ssl_broker_int, - ssl_broker_sup, - ssl_debug, - ssl_server, - ssl_prim, - inet_ssl_dist, - 'OTP-PKIX' +{incl_app,ssl,details}. + +{excl_mods, ssl, [ssl_pkix_oid, + 'PKIX1Algorithms88', + 'PKIX1Explicit88', + 'PKIX1Implicit88', + 'PKIXAttributeCertificate', + 'SSL-PKIX', + ssl_pem, + ssl_pkix, + ssl_base64, + ssl_broker, + ssl_broker_int, + ssl_broker_sup, + ssl_debug, + ssl_server, + ssl_prim, + inet_ssl_dist, + 'OTP-PKIX' ]}. diff --git a/lib/ssl/test/ssl.spec b/lib/ssl/test/ssl.spec index 6ef4fb73db..fc7c1bbb82 100644 --- a/lib/ssl/test/ssl.spec +++ b/lib/ssl/test/ssl.spec @@ -1 +1 @@ -{topcase, {dir, "../ssl_test"}}. +{suites,"../ssl_test",all}. diff --git a/lib/ssl/test/ssl_basic_SUITE.erl b/lib/ssl/test/ssl_basic_SUITE.erl index 6a1b83d344..4f0907027f 100644 --- a/lib/ssl/test/ssl_basic_SUITE.erl +++ b/lib/ssl/test/ssl_basic_SUITE.erl @@ -24,11 +24,12 @@ %% Note: This directive should only be used in test suites. -compile(export_all). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -include("test_server_line.hrl"). -include_lib("public_key/include/public_key.hrl"). -include("ssl_alert.hrl"). +-include("ssl_int.hrl"). -define('24H_in_sec', 86400). -define(TIMEOUT, 60000). @@ -48,7 +49,7 @@ %%-------------------------------------------------------------------- init_per_suite(Config0) -> Dog = ssl_test_lib:timetrap(?LONG_TIMEOUT *2), - case application:start(crypto) of + try crypto:start() of ok -> application:start(public_key), ssl:start(), @@ -61,8 +62,8 @@ init_per_suite(Config0) -> Config1 = ssl_test_lib:make_dsa_cert(Config0), Config = ssl_test_lib:cert_options(Config1), - [{watchdog, Dog} | Config]; - _ -> + [{watchdog, Dog} | Config] + catch _:_ -> {skip, "Crypto did not start"} end. %%-------------------------------------------------------------------- @@ -88,6 +89,13 @@ end_per_suite(_Config) -> %% variable, but should NOT alter/remove any existing entries. %% Description: Initialization before each test case %%-------------------------------------------------------------------- +init_per_testcase(session_cache_process_list, Config) -> + init_customized_session_cache(list, Config); + +init_per_testcase(session_cache_process_mnesia, Config) -> + mnesia:start(), + init_customized_session_cache(mnesia, Config); + init_per_testcase(reuse_session_expired, Config0) -> Config = lists:keydelete(watchdog, 1, Config0), Dog = ssl_test_lib:timetrap(?EXPIRE * 1000 * 5), @@ -137,6 +145,16 @@ init_per_testcase(_TestCase, Config0) -> Dog = test_server:timetrap(?TIMEOUT), [{watchdog, Dog} | Config]. +init_customized_session_cache(Type, Config0) -> + Config = lists:keydelete(watchdog, 1, Config0), + Dog = test_server:timetrap(?TIMEOUT), + ssl:stop(), + application:load(ssl), + application:set_env(ssl, session_cb, ?MODULE), + application:set_env(ssl, session_cb_init_args, [Type]), + ssl:start(), + [{watchdog, Dog} | Config]. + %%-------------------------------------------------------------------- %% Function: end_per_testcase(TestCase, Config) -> _ %% Case - atom() @@ -145,6 +163,16 @@ init_per_testcase(_TestCase, Config0) -> %% A list of key/value pairs, holding the test case configuration. %% Description: Cleanup after each test case %%-------------------------------------------------------------------- +end_per_testcase(session_cache_process_list, Config) -> + application:unset_env(ssl, session_cb), + end_per_testcase(default_action, Config); +end_per_testcase(session_cache_process_mnesia, Config) -> + application:unset_env(ssl, session_cb), + application:unset_env(ssl, session_cb_init_args), + mnesia:stop(), + ssl:stop(), + ssl:start(), + end_per_testcase(default_action, Config); end_per_testcase(reuse_session_expired, Config) -> application:unset_env(ssl, session_lifetime), end_per_testcase(default_action, Config); @@ -173,52 +201,69 @@ end_per_testcase(_TestCase, Config) -> %% Name of a test case. %% Description: Returns a list of all test cases in this test suite %%-------------------------------------------------------------------- -all(doc) -> - ["Test the basic ssl functionality"]; +suite() -> [{ct_hooks,[ts_install_cth]}]. -all(suite) -> +all() -> [app, alerts, connection_info, protocol_versions, - empty_protocol_versions, controlling_process, controller_dies, - client_closes_socket, peercert, connect_dist, peername, sockname, - socket_options, misc_ssl_options, versions, cipher_suites, - upgrade, upgrade_with_timeout, tcp_connect, ipv6, ekeyfile, - ecertfile, ecacertfile, eoptions, shutdown, shutdown_write, - shutdown_both, shutdown_error, + empty_protocol_versions, controlling_process, + controller_dies, client_closes_socket, peercert, + connect_dist, peername, sockname, socket_options, + misc_ssl_options, versions, cipher_suites, upgrade, + upgrade_with_timeout, tcp_connect, ipv6, ekeyfile, + ecertfile, ecacertfile, eoptions, shutdown, + shutdown_write, shutdown_both, shutdown_error, ciphers_rsa_signed_certs, ciphers_rsa_signed_certs_ssl3, ciphers_rsa_signed_certs_openssl_names, ciphers_rsa_signed_certs_openssl_names_ssl3, - ciphers_dsa_signed_certs, - ciphers_dsa_signed_certs_ssl3, + ciphers_dsa_signed_certs, ciphers_dsa_signed_certs_ssl3, ciphers_dsa_signed_certs_openssl_names, ciphers_dsa_signed_certs_openssl_names_ssl3, anonymous_cipher_suites, default_reject_anonymous, send_close, - close_transport_accept, dh_params, server_verify_peer_passive, - server_verify_peer_active, server_verify_peer_active_once, + close_transport_accept, dh_params, + server_verify_peer_passive, server_verify_peer_active, + server_verify_peer_active_once, server_verify_none_passive, server_verify_none_active, - server_verify_none_active_once, server_verify_no_cacerts, - server_require_peer_cert_ok, server_require_peer_cert_fail, + server_verify_none_active_once, + server_verify_no_cacerts, server_require_peer_cert_ok, + server_require_peer_cert_fail, server_verify_client_once_passive, server_verify_client_once_active, - server_verify_client_once_active_once, client_verify_none_passive, - client_verify_none_active, client_verify_none_active_once, - reuse_session, reuse_session_expired, - server_does_not_want_to_reuse_session, client_renegotiate, - server_renegotiate, client_renegotiate_reused_session, - server_renegotiate_reused_session, client_no_wrap_sequence_number, - server_no_wrap_sequence_number, - extended_key_usage_verify_peer, extended_key_usage_verify_none, - no_authority_key_identifier, - invalid_signature_client, invalid_signature_server, cert_expired, - client_with_cert_cipher_suites_handshake, unknown_server_ca_fail, - der_input, unknown_server_ca_accept_verify_none, unknown_server_ca_accept_verify_peer, + server_verify_client_once_active_once, + client_verify_none_passive, client_verify_none_active, + client_verify_none_active_once, + reuse_session, + reuse_session_expired, + server_does_not_want_to_reuse_session, + client_renegotiate, server_renegotiate, + client_renegotiate_reused_session, + server_renegotiate_reused_session, + client_no_wrap_sequence_number, + server_no_wrap_sequence_number, extended_key_usage_verify_peer, + extended_key_usage_verify_none, + no_authority_key_identifier, invalid_signature_client, + invalid_signature_server, cert_expired, + client_with_cert_cipher_suites_handshake, + unknown_server_ca_fail, der_input, + unknown_server_ca_accept_verify_none, + unknown_server_ca_accept_verify_peer, unknown_server_ca_accept_backwardscompatibilty, - %different_ca_peer_sign, + %%different_ca_peer_sign, no_reuses_session_server_restart_new_cert, - no_reuses_session_server_restart_new_cert_file, reuseaddr + no_reuses_session_server_restart_new_cert_file, reuseaddr, + hibernate ]. +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + %% Test cases starts here. %%-------------------------------------------------------------------- app(doc) -> @@ -1059,6 +1104,8 @@ dummy(_Socket) -> exit(kill). %%-------------------------------------------------------------------- +ipv6() -> + [{require, ipv6_hosts}]. ipv6(doc) -> ["Test ipv6."]; ipv6(suite) -> @@ -1066,7 +1113,7 @@ ipv6(suite) -> ipv6(Config) when is_list(Config) -> {ok, Hostname0} = inet:gethostname(), - case lists:member(list_to_atom(Hostname0), ?config(ipv6_hosts, Config)) of + case lists:member(list_to_atom(Hostname0), ct:get_config(ipv6_hosts)) of true -> ClientOpts = ?config(client_opts, Config), ServerOpts = ?config(server_opts, Config), @@ -3275,19 +3322,47 @@ reuseaddr(Config) when is_list(Config) -> ssl_test_lib:close(Client1). %%-------------------------------------------------------------------- + +hibernate(doc) -> + ["Check that an SSL connection that is started with option " + "{hibernate_after, 1000} indeed hibernates after 1000ms of " + "inactivity"]; + +hibernate(suite) -> + []; + +hibernate(Config) -> + ClientOpts = ?config(client_opts, Config), + ServerOpts = ?config(server_opts, Config), + + {ClientNode, ServerNode, Hostname} = ssl_test_lib:run_where(Config), + + Server = ssl_test_lib:start_server([{node, ServerNode}, {port, 0}, + {from, self()}, + {mfa, {?MODULE, send_recv_result_active, []}}, + {options, ServerOpts}]), + Port = ssl_test_lib:inet_port(Server), + {Client, #sslsocket{pid=Pid}} = ssl_test_lib:start_client([return_socket, + {node, ClientNode}, {port, Port}, + {host, Hostname}, + {from, self()}, + {mfa, {?MODULE, send_recv_result_active, []}}, + {options, [{hibernate_after, 1000}|ClientOpts]}]), + + { current_function, { _M, _F, _A } } = + process_info(Pid, current_function), + + timer:sleep(1100), + + { current_function, { erlang, hibernate, 3} } = + process_info(Pid, current_function), + + ssl_test_lib:close(Server), + ssl_test_lib:close(Client). + +%%-------------------------------------------------------------------- %%% Internal functions %%-------------------------------------------------------------------- -erlang_ssl_receive(Socket, Data) -> - receive - {ssl, Socket, Data} -> - test_server:format("Received ~p~n",[Data]), - ok; - Other -> - test_server:fail({unexpected_message, Other}) - after ?SLEEP * 3 -> - test_server:fail({did_not_get, Data}) - end. - send_recv_result(Socket) -> ssl:send(Socket, "Hello world"), {ok,"Hello world"} = ssl:recv(Socket, 11), @@ -3327,7 +3402,6 @@ renegotiate_reuse_session(Socket, Data) -> test_server:sleep(?SLEEP), renegotiate(Socket, Data). - new_config(PrivDir, ServerOpts0) -> CaCertFile = proplists:get_value(cacertfile, ServerOpts0), CertFile = proplists:get_value(certfile, ServerOpts0), @@ -3347,3 +3421,162 @@ new_config(PrivDir, ServerOpts0) -> [{cacertfile, NewCaCertFile}, {certfile, NewCertFile}, {keyfile, NewKeyFile} | ServerOpts]. + +session_cache_process_list(doc) -> + ["Test reuse of sessions (short handshake)"]; + +session_cache_process_list(suite) -> + []; +session_cache_process_list(Config) when is_list(Config) -> + session_cache_process(list,Config). + +session_cache_process_mnesia(doc) -> + ["Test reuse of sessions (short handshake)"]; + +session_cache_process_mnesia(suite) -> + []; +session_cache_process_mnesia(Config) when is_list(Config) -> + session_cache_process(mnesia,Config). + +session_cache_process(Type,Config) when is_list(Config) -> + reuse_session(Config). + +init([Type]) -> + ets:new(ssl_test, [named_table, public, set]), + ets:insert(ssl_test, {type, Type}), + case Type of + list -> + spawn(fun() -> session_loop([]) end); + mnesia -> + mnesia:start(), + {atomic,ok} = mnesia:create_table(sess_cache, []), + sess_cache + end. + +session_cb() -> + [{type, Type}] = ets:lookup(ssl_test, type), + Type. + +terminate(Cache) -> + case session_cb() of + list -> + Cache ! terminate; + mnesia -> + catch {atomic,ok} = + mnesia:delete_table(sess_cache) + end. + +lookup(Cache, Key) -> + case session_cb() of + list -> + Cache ! {self(), lookup, Key}, + receive {Cache, Res} -> Res end; + mnesia -> + case mnesia:transaction(fun() -> + mnesia:read(sess_cache, + Key, read) + end) of + {atomic, [{sess_cache, Key, Value}]} -> + Value; + _ -> + undefined + end + end. + +update(Cache, Key, Value) -> + case session_cb() of + list -> + Cache ! {update, Key, Value}; + mnesia -> + {atomic, ok} = + mnesia:transaction(fun() -> + mnesia:write(sess_cache, + {sess_cache, Key, Value}, write) + end) + end. + +delete(Cache, Key) -> + case session_cb() of + list -> + Cache ! {delete, Key}; + mnesia -> + {atomic, ok} = + mnesia:transaction(fun() -> + mnesia:delete(sess_cache, Key) + end) + end. + +foldl(Fun, Acc, Cache) -> + case session_cb() of + list -> + Cache ! {self(),foldl,Fun,Acc}, + receive {Cache, Res} -> Res end; + mnesia -> + Foldl = fun() -> + mnesia:foldl(Fun, Acc, sess_cache) + end, + {atomic, Res} = mnesia:transaction(Foldl), + Res + end. + +select_session(Cache, PartialKey) -> + case session_cb() of + list -> + Cache ! {self(),select_session, PartialKey}, + receive + {Cache, Res} -> + Res + end; + mnesia -> + Sel = fun() -> + mnesia:select(Cache, + [{{sess_cache,{PartialKey,'$1'}, '$2'}, + [],['$$']}]) + end, + {atomic, Res} = mnesia:transaction(Sel), + Res + end. + +session_loop(Sess) -> + receive + terminate -> + ok; + {Pid, lookup, Key} -> + case lists:keysearch(Key,1,Sess) of + {value, {Key,Value}} -> + Pid ! {self(), Value}; + _ -> + Pid ! {self(), undefined} + end, + session_loop(Sess); + {update, Key, Value} -> + NewSess = [{Key,Value}| lists:keydelete(Key,1,Sess)], + session_loop(NewSess); + {delete, Key} -> + session_loop(lists:keydelete(Key,1,Sess)); + {Pid,foldl,Fun,Acc} -> + Res = lists:foldl(Fun, Acc,Sess), + Pid ! {self(), Res}, + session_loop(Sess); + {Pid,select_session,PKey} -> + Sel = fun({{PKey0, Id},Session}, Acc) when PKey == PKey0 -> + [[Id, Session]|Acc]; + (_,Acc) -> + Acc + end, + Sessions = lists:foldl(Sel, [], Sess), + Pid ! {self(), Sessions}, + session_loop(Sess) + end. + + +erlang_ssl_receive(Socket, Data) -> + receive + {ssl, Socket, Data} -> + io:format("Received ~p~n",[Data]), + ok; + Other -> + test_server:fail({unexpected_message, Other}) + after ?SLEEP * 3 -> + test_server:fail({did_not_get, Data}) + end. diff --git a/lib/ssl/test/ssl_packet_SUITE.erl b/lib/ssl/test/ssl_packet_SUITE.erl index b1e585e39e..d22d5d2954 100644 --- a/lib/ssl/test/ssl_packet_SUITE.erl +++ b/lib/ssl/test/ssl_packet_SUITE.erl @@ -23,7 +23,7 @@ %% Note: This directive should only be used in test suites. -compile(export_all). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -define(BYTE(X), X:8/unsigned-big-integer). -define(UINT16(X), X:16/unsigned-big-integer). @@ -53,7 +53,7 @@ %% variable, but should NOT alter/remove any existing entries. %%-------------------------------------------------------------------- init_per_suite(Config) -> - case application:start(crypto) of + try crypto:start() of ok -> application:start(public_key), ssl:start(), @@ -61,8 +61,8 @@ init_per_suite(Config) -> (catch make_certs:all(?config(data_dir, Config), ?config(priv_dir, Config))), test_server:format("Make certs ~p~n", [Result]), - ssl_test_lib:cert_options(Config); - _ -> + ssl_test_lib:cert_options(Config) + catch _:_ -> {skip, "Crypto did not start"} end. %%-------------------------------------------------------------------- @@ -118,56 +118,56 @@ end_per_testcase(_TestCase, Config) -> %% Name of a test case. %% Description: Returns a list of all test cases in this test suite %%-------------------------------------------------------------------- -all(doc) -> - ["Test that erlang:decode_packet/3 seems to be handled correctly." - "We only use the most basic packet types in our tests as testing of" - "the packet types are for inet to verify" - ]; - -all(suite) -> - [packet_raw_passive_many_small, - packet_0_passive_many_small, packet_1_passive_many_small, - packet_2_passive_many_small, packet_4_passive_many_small, - packet_raw_passive_some_big, packet_0_passive_some_big, - packet_1_passive_some_big, - packet_2_passive_some_big, packet_4_passive_some_big, - packet_raw_active_once_many_small, - packet_0_active_once_many_small, packet_1_active_once_many_small, - packet_2_active_once_many_small, packet_4_active_once_many_small, - packet_raw_active_once_some_big, - packet_0_active_once_some_big, packet_1_active_once_some_big, - packet_2_active_once_some_big, packet_4_active_once_some_big, - packet_raw_active_many_small, packet_0_active_many_small, - packet_1_active_many_small, +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [packet_raw_passive_many_small, + packet_0_passive_many_small, + packet_1_passive_many_small, + packet_2_passive_many_small, + packet_4_passive_many_small, + packet_raw_passive_some_big, packet_0_passive_some_big, + packet_1_passive_some_big, packet_2_passive_some_big, + packet_4_passive_some_big, + packet_raw_active_once_many_small, + packet_0_active_once_many_small, + packet_1_active_once_many_small, + packet_2_active_once_many_small, + packet_4_active_once_many_small, + packet_raw_active_once_some_big, + packet_0_active_once_some_big, + packet_1_active_once_some_big, + packet_2_active_once_some_big, + packet_4_active_once_some_big, + packet_raw_active_many_small, + packet_0_active_many_small, packet_1_active_many_small, packet_2_active_many_small, packet_4_active_many_small, - packet_raw_active_some_big, packet_0_active_some_big, - packet_1_active_some_big, packet_2_active_some_big, - packet_4_active_some_big, - packet_send_to_large, + packet_raw_active_some_big, packet_0_active_some_big, + packet_1_active_some_big, packet_2_active_some_big, + packet_4_active_some_big, packet_send_to_large, packet_wait_passive, packet_wait_active, packet_baddata_passive, packet_baddata_active, packet_size_passive, packet_size_active, - packet_cdr_decode, - packet_cdr_decode_list, - packet_http_decode, - packet_http_decode_list, - packet_http_bin_decode_multi, - packet_http_error_passive, - packet_line_decode, - packet_line_decode_list, - packet_asn1_decode, - packet_asn1_decode_list, - packet_tpkt_decode, - packet_tpkt_decode_list, - %packet_fcgi_decode, - packet_sunrm_decode, - packet_sunrm_decode_list, - header_decode_one_byte, - header_decode_two_bytes, + packet_cdr_decode, packet_cdr_decode_list, + packet_http_decode, packet_http_decode_list, + packet_http_bin_decode_multi, packet_http_error_passive, + packet_line_decode, packet_line_decode_list, + packet_asn1_decode, packet_asn1_decode_list, + packet_tpkt_decode, packet_tpkt_decode_list, + packet_sunrm_decode, packet_sunrm_decode_list, + header_decode_one_byte, header_decode_two_bytes, header_decode_two_bytes_one_sent, - header_decode_two_bytes_two_sent + header_decode_two_bytes_two_sent]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. - ]. %% Test cases starts here. %%-------------------------------------------------------------------- diff --git a/lib/ssl/test/ssl_payload_SUITE.erl b/lib/ssl/test/ssl_payload_SUITE.erl index b19d1f286f..24e86b3913 100644 --- a/lib/ssl/test/ssl_payload_SUITE.erl +++ b/lib/ssl/test/ssl_payload_SUITE.erl @@ -22,7 +22,7 @@ %% Note: This directive should only be used in test suites. -compile(export_all). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -define(TIMEOUT, 600000). @@ -37,13 +37,13 @@ %% variable, but should NOT alter/remove any existing entries. %%-------------------------------------------------------------------- init_per_suite(Config) -> - case application:start(crypto) of + try crypto:start() of ok -> application:start(public_key), ssl:start(), make_certs:all(?config(data_dir, Config), ?config(priv_dir, Config)), - ssl_test_lib:cert_options(Config); - _ -> + ssl_test_lib:cert_options(Config) + catch _:_ -> {skip, "Crypto did not start"} end. %%-------------------------------------------------------------------- @@ -99,24 +99,30 @@ end_per_testcase(_TestCase, Config) -> %% Name of a test case. %% Description: Returns a list of all test cases in this test suite %%-------------------------------------------------------------------- -all(doc) -> - ["Test payload over ssl in all socket modes, active, active_once," - "and passive mode."]; - -all(suite) -> - [server_echos_passive_small, server_echos_active_once_small, - server_echos_active_small, - client_echos_passive_small, client_echos_active_once_small, - client_echos_active_small, - server_echos_passive_big, server_echos_active_once_big, - server_echos_active_big, - client_echos_passive_big, client_echos_active_once_big, - client_echos_active_big, - server_echos_passive_huge, server_echos_active_once_huge, - server_echos_active_huge, - client_echos_passive_huge, client_echos_active_once_huge, - client_echos_active_huge - ]. +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [server_echos_passive_small, + server_echos_active_once_small, + server_echos_active_small, client_echos_passive_small, + client_echos_active_once_small, + client_echos_active_small, server_echos_passive_big, + server_echos_active_once_big, server_echos_active_big, + client_echos_passive_big, client_echos_active_once_big, + client_echos_active_big, server_echos_passive_huge, + server_echos_active_once_huge, server_echos_active_huge, + client_echos_passive_huge, + client_echos_active_once_huge, client_echos_active_huge]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + %% Test cases starts here. %%-------------------------------------------------------------------- diff --git a/lib/ssl/test/ssl_session_cache_SUITE.erl b/lib/ssl/test/ssl_session_cache_SUITE.erl index 5aac9bb4e3..a43b9ab586 100644 --- a/lib/ssl/test/ssl_session_cache_SUITE.erl +++ b/lib/ssl/test/ssl_session_cache_SUITE.erl @@ -24,7 +24,7 @@ %% Note: This directive should only be used in test suites. -compile(export_all). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -define(SLEEP, 500). -define(TIMEOUT, 60000). @@ -47,7 +47,7 @@ %%-------------------------------------------------------------------- init_per_suite(Config0) -> Dog = ssl_test_lib:timetrap(?LONG_TIMEOUT *2), - case application:start(crypto) of + try crypto:start() of ok -> application:start(public_key), ssl:start(), @@ -60,8 +60,8 @@ init_per_suite(Config0) -> Config1 = ssl_test_lib:make_dsa_cert(Config0), Config = ssl_test_lib:cert_options(Config1), - [{watchdog, Dog} | Config]; - _ -> + [{watchdog, Dog} | Config] + catch _:_ -> {skip, "Crypto did not start"} end. @@ -145,13 +145,20 @@ end_per_testcase(_TestCase, Config) -> %% Name of a test case. %% Description: Returns a list of all test cases in this test suite %%-------------------------------------------------------------------- -all(doc) -> - ["Test session cach API"]; +suite() -> [{ct_hooks,[ts_install_cth]}]. + +all() -> + [session_cache_process_list, + session_cache_process_mnesia]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. -all(suite) -> - [ - session_cache_process_list, session_cache_process_mnesia - ]. +end_per_group(_GroupName, Config) -> + Config. session_cache_process_list(doc) -> ["Test reuse of sessions (short handshake)"]; diff --git a/lib/ssl/test/ssl_test_lib.erl b/lib/ssl/test/ssl_test_lib.erl index f6ccbe85e3..40bbdf1dbd 100644 --- a/lib/ssl/test/ssl_test_lib.erl +++ b/lib/ssl/test/ssl_test_lib.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2008-2010. All Rights Reserved. +%% Copyright Ericsson AB 2008-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -128,12 +128,14 @@ remove_close_msg(ReconnectTimes) -> remove_close_msg(ReconnectTimes -1) end. - start_client(Args) -> - Result = spawn_link(?MODULE, run_client, [Args]), + Result = spawn_link(?MODULE, run_client, [lists:delete(return_socket, Args)]), receive - connected -> - Result + { connected, Socket } -> + case lists:member(return_socket, Args) of + true -> { Result, Socket }; + false -> Result + end end. run_client(Opts) -> @@ -145,7 +147,7 @@ run_client(Opts) -> test_server:format("ssl:connect(~p, ~p, ~p)~n", [Host, Port, Options]), case rpc:call(Node, ssl, connect, [Host, Port, Options]) of {ok, Socket} -> - Pid ! connected, + Pid ! { connected, Socket }, test_server:format("Client: connected~n", []), %% In specail cases we want to know the client port, it will %% be indicated by sending {port, 0} in options list! diff --git a/lib/ssl/test/ssl_to_openssl_SUITE.erl b/lib/ssl/test/ssl_to_openssl_SUITE.erl index 0cbaafd99c..64a6a9eaf8 100644 --- a/lib/ssl/test/ssl_to_openssl_SUITE.erl +++ b/lib/ssl/test/ssl_to_openssl_SUITE.erl @@ -24,7 +24,7 @@ %% Note: This directive should only be used in test suites. -compile(export_all). --include("test_server.hrl"). +-include_lib("common_test/include/ct.hrl"). -define(TIMEOUT, 120000). -define(LONG_TIMEOUT, 600000). @@ -50,7 +50,7 @@ init_per_suite(Config0) -> false -> {skip, "Openssl not found"}; _ -> - case application:start(crypto) of + try crypto:start() of ok -> application:start(public_key), ssl:start(), @@ -60,8 +60,8 @@ init_per_suite(Config0) -> test_server:format("Make certs ~p~n", [Result]), Config1 = ssl_test_lib:make_dsa_cert(Config0), Config = ssl_test_lib:cert_options(Config1), - [{watchdog, Dog} | Config]; - _ -> + [{watchdog, Dog} | Config] + catch _:_ -> {skip, "Crypto did not start"} end end. @@ -143,11 +143,10 @@ end_per_testcase(_, Config) -> %% Name of a test case. %% Description: Returns a list of all test cases in this test suite %%-------------------------------------------------------------------- -all(doc) -> - ["Test erlangs ssl against openssl"]; +suite() -> [{ct_hooks,[ts_install_cth]}]. -all(suite) -> - [erlang_client_openssl_server, +all() -> + [erlang_client_openssl_server, erlang_server_openssl_client, tls1_erlang_client_openssl_server_dsa_cert, tls1_erlang_server_openssl_client_dsa_cert, @@ -158,22 +157,29 @@ all(suite) -> erlang_client_openssl_server_no_wrap_sequence_number, erlang_server_openssl_client_no_wrap_sequence_number, erlang_client_openssl_server_no_server_ca_cert, - ssl3_erlang_client_openssl_server, + ssl3_erlang_client_openssl_server, ssl3_erlang_server_openssl_client, ssl3_erlang_client_openssl_server_client_cert, ssl3_erlang_server_openssl_client_client_cert, ssl3_erlang_server_erlang_client_client_cert, - tls1_erlang_client_openssl_server, + tls1_erlang_client_openssl_server, tls1_erlang_server_openssl_client, tls1_erlang_client_openssl_server_client_cert, tls1_erlang_server_openssl_client_client_cert, tls1_erlang_server_erlang_client_client_cert, - ciphers_rsa_signed_certs, - ciphers_dsa_signed_certs, - erlang_client_bad_openssl_server, - expired_session, - ssl2_erlang_server_openssl_client - ]. + ciphers_rsa_signed_certs, ciphers_dsa_signed_certs, + erlang_client_bad_openssl_server, expired_session, + ssl2_erlang_server_openssl_client]. + +groups() -> + []. + +init_per_group(_GroupName, Config) -> + Config. + +end_per_group(_GroupName, Config) -> + Config. + %% Test cases starts here. %%-------------------------------------------------------------------- diff --git a/lib/ssl/vsn.mk b/lib/ssl/vsn.mk index a4be7bb889..2f1edfa186 100644 --- a/lib/ssl/vsn.mk +++ b/lib/ssl/vsn.mk @@ -1,2 +1 @@ - -SSL_VSN = 4.1.3 +SSL_VSN = 4.1.4 |
