diff options
33 files changed, 308 insertions, 231 deletions
diff --git a/README.bootstrap b/README.bootstrap index b0c8a1cc20..f42bc7aa47 100644 --- a/README.bootstrap +++ b/README.bootstrap @@ -45,13 +45,11 @@ preloaded files are to be updated, the source code is built using a special Makefile in the $ERL_TOP/preloaded/src directory, which creates beam files in the same directory. When they seem to compile successfully, they can be used in an emulator build by being copied -to the ebin directory (although, in Clearcase that requires checking -out the files in the ebin directory first). For developers using the -main Clearcase branch, otp_build {prepare,update,commit}_preloaded can -be used to ease the process (there are also similar targets in the +to the ebin directory. otp_build update_preloaded can be used to +ease the process (there are also similar targets in the $ERL_TOP/preloaded/src/Makefile). -In prebuilt open source distributions, these .beam files are also +In prebuilt open source distributions, these beam files are also present, but to update them one might need to change permission on the $ERL_TOP/preloaded/ebin directory, then build and then manually copy the beam files from the source directory to ../ebin. If patches are @@ -60,4 +58,4 @@ always note this specially as the preloaded/ebin directory needs updating, or provide the new derived files in the patch or as complete binaries. -/Patrik, OTP
\ No newline at end of file +/Patrik, OTP diff --git a/erts/emulator/beam/global.h b/erts/emulator/beam/global.h index 280421952e..ecd3c8f68a 100644 --- a/erts/emulator/beam/global.h +++ b/erts/emulator/beam/global.h @@ -1499,7 +1499,7 @@ erts_cmp_timeval(SysTimeval *t1p, SysTimeval *t2p) #endif #ifdef DEBUG -void p_slpq(_VOID_); +void p_slpq(void); #endif /* utils.c */ diff --git a/erts/preloaded/src/Makefile b/erts/preloaded/src/Makefile index 785ad531f3..145638802f 100644 --- a/erts/preloaded/src/Makefile +++ b/erts/preloaded/src/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 2008-2009. All Rights Reserved. +# Copyright Ericsson AB 2008-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 @@ -20,8 +20,7 @@ # be used when the preloaded modules actually are to be updated (i.e. the # beam files are to be recompiled, which is normally not done). # The beam files are placed in the current directory and should be copied -# to the ../ebin directory by using the commit target (only works in -# clearcase). +# to the ../ebin directory by using the copy target. include $(ERL_TOP)/make/target.mk include $(ERL_TOP)/make/$(TARGET)/otp.mk @@ -62,26 +61,9 @@ debug opt: $(TARGET_FILES) clean: rm -f $(TARGET_FILES) -prepare: - cleartool co -nc $(STATIC_EBIN)/* - cleartool co -nc $(STATIC_EBIN) - copy: - for x in *.beam; do\ - if test '!' -f $(STATIC_EBIN)/$$x; then\ - cleartool mkelem -nc $$x;\ - fi;\ - done cp *.beam $(STATIC_EBIN) -commit: - cleartool ci -ident -nc $(STATIC_EBIN)/*.beam - cleartool ci -ident -nc $(STATIC_EBIN) - -cancel: - -cleartool unco -rm $(STATIC_EBIN) - -cleartool unco -rm $(STATIC_EBIN)/*.beam - include $(ERL_TOP)/make/otp_release_targets.mk diff --git a/erts/vsn.mk b/erts/vsn.mk index ce6330e6dd..a5dd62feb2 100644 --- a/erts/vsn.mk +++ b/erts/vsn.mk @@ -17,8 +17,8 @@ # %CopyrightEnd% # -VSN = 5.8.1 -SYSTEM_VSN = R14B +VSN = 5.8.2 +SYSTEM_VSN = R14B01 # Port number 4365 in 4.2 # Port number 4366 in 4.3 diff --git a/lib/edoc/src/edoc.erl b/lib/edoc/src/edoc.erl index ec452a5929..75b3bb451a 100644 --- a/lib/edoc/src/edoc.erl +++ b/lib/edoc/src/edoc.erl @@ -58,6 +58,8 @@ read_comments/1, read_comments/2, read_source/1, read_source/2]). +-compile({no_auto_import,[error/1]}). + -import(edoc_report, [report/2, report/3, error/1, error/3]). -include("edoc.hrl"). diff --git a/lib/edoc/src/edoc_run.erl b/lib/edoc/src/edoc_run.erl index 37025d6621..96e5ea4631 100644 --- a/lib/edoc/src/edoc_run.erl +++ b/lib/edoc/src/edoc_run.erl @@ -42,6 +42,8 @@ -export([file/1, application/1, packages/1, files/1, toc/1]). +-compile({no_auto_import,[error/1]}). + -import(edoc_report, [report/2, error/1]). diff --git a/lib/hipe/icode/hipe_icode_type.erl b/lib/hipe/icode/hipe_icode_type.erl index 28198467f7..6726d62b53 100644 --- a/lib/hipe/icode/hipe_icode_type.erl +++ b/lib/hipe/icode/hipe_icode_type.erl @@ -39,6 +39,8 @@ update__info/2, new__info/1, return__info/1, return_none/0, return_none_args/2, return_any_args/2]). +-compile({no_auto_import,[min/2,max/2]}). + %%===================================================================== -include("../main/hipe.hrl"). diff --git a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpMbox.java b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpMbox.java index 4146bd3ced..a9712aa2ba 100644 --- a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpMbox.java +++ b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpMbox.java @@ -678,6 +678,11 @@ public class OtpMbox { return m.self.equals(self); } + @Override + public int hashCode() { + return self.hashCode(); + } + /* * called by OtpNode to deliver message to this mailbox. * diff --git a/lib/kernel/vsn.mk b/lib/kernel/vsn.mk index 651d082379..03fe63e385 100644 --- a/lib/kernel/vsn.mk +++ b/lib/kernel/vsn.mk @@ -1 +1 @@ -KERNEL_VSN = 2.14.1 +KERNEL_VSN = 2.14.2 diff --git a/lib/mnesia/src/mnesia_controller.erl b/lib/mnesia/src/mnesia_controller.erl index 0298b382a6..021be8af2a 100644 --- a/lib/mnesia/src/mnesia_controller.erl +++ b/lib/mnesia/src/mnesia_controller.erl @@ -98,6 +98,8 @@ connect_nodes2/3 ]). +-compile({no_auto_import,[error/2]}). + -import(mnesia_lib, [set/2, add/2]). -import(mnesia_lib, [fatal/2, error/2, verbose/2, dbg_out/2]). diff --git a/lib/mnesia/src/mnesia_locker.erl b/lib/mnesia/src/mnesia_locker.erl index cfa3f171b2..6b5770d91e 100644 --- a/lib/mnesia/src/mnesia_locker.erl +++ b/lib/mnesia/src/mnesia_locker.erl @@ -49,6 +49,8 @@ system_code_change/4 ]). +-compile({no_auto_import,[error/2]}). + -include("mnesia.hrl"). -import(mnesia_lib, [dbg_out/2, error/2, verbose/2]). diff --git a/lib/mnesia/src/mnesia_log.erl b/lib/mnesia/src/mnesia_log.erl index 00ec4740ee..11b792026e 100644 --- a/lib/mnesia/src/mnesia_log.erl +++ b/lib/mnesia/src/mnesia_log.erl @@ -182,6 +182,8 @@ ]). +-compile({no_auto_import,[error/2]}). + -include("mnesia.hrl"). -import(mnesia_lib, [val/1, dir/1]). -import(mnesia_lib, [exists/1, fatal/2, error/2, dbg_out/2]). diff --git a/lib/mnesia/src/mnesia_monitor.erl b/lib/mnesia/src/mnesia_monitor.erl index 5bd93d6b9b..b6eda9ad3a 100644 --- a/lib/mnesia/src/mnesia_monitor.erl +++ b/lib/mnesia/src/mnesia_monitor.erl @@ -70,6 +70,8 @@ negotiate_protocol_impl/2 ]). +-compile({no_auto_import,[error/2]}). + -import(mnesia_lib, [dbg_out/2, verbose/2, error/2, fatal/2, set/2]). -include("mnesia.hrl"). diff --git a/lib/mnesia/src/mnesia_recover.erl b/lib/mnesia/src/mnesia_recover.erl index 0ca7bf3f7f..7435b6896a 100644 --- a/lib/mnesia/src/mnesia_recover.erl +++ b/lib/mnesia/src/mnesia_recover.erl @@ -62,6 +62,7 @@ code_change/3 ]). +-compile({no_auto_import,[error/2]}). -include("mnesia.hrl"). -import(mnesia_lib, [set/2, verbose/2, error/2, fatal/2]). diff --git a/lib/mnesia/src/mnesia_subscr.erl b/lib/mnesia/src/mnesia_subscr.erl index 93d4a86f7f..415c69d508 100644 --- a/lib/mnesia/src/mnesia_subscr.erl +++ b/lib/mnesia/src/mnesia_subscr.erl @@ -43,6 +43,8 @@ code_change/3 ]). +-compile({no_auto_import,[error/2]}). + -include("mnesia.hrl"). -import(mnesia_lib, [error/2]). diff --git a/lib/observer/src/Makefile b/lib/observer/src/Makefile index dde1ea17be..b4eb518dd7 100644 --- a/lib/observer/src/Makefile +++ b/lib/observer/src/Makefile @@ -111,7 +111,8 @@ release_spec: opt $(INSTALL_DIR) $(RELSYSDIR)/src $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src - $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/src + $(INSTALL_DIR) $(RELSYSDIR)/examples + $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/examples $(INSTALL_DIR) $(RELSYSDIR)/include $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include $(INSTALL_DIR) $(RELSYSDIR)/ebin diff --git a/lib/public_key/asn1/OTP-PKIX.asn1 b/lib/public_key/asn1/OTP-PKIX.asn1 index c0cf440496..ad704191a9 100644 --- a/lib/public_key/asn1/OTP-PKIX.asn1 +++ b/lib/public_key/asn1/OTP-PKIX.asn1 @@ -302,18 +302,25 @@ SupportedPublicKeyAlgorithms PUBLIC-KEY-ALGORITHM-CLASS ::= { -- DSA Keys and Signatures + + DSAParams ::= CHOICE + { + params Dss-Parms, + null NULL + } + -- SubjectPublicKeyInfo: dsa PUBLIC-KEY-ALGORITHM-CLASS ::= { ID id-dsa - TYPE Dss-Parms -- XXX Must be OPTIONAL + TYPE DSAParams -- XXX Must be OPTIONAL PUBLIC-KEY-TYPE DSAPublicKey } -- Certificate.signatureAlgorithm dsa-with-sha1 SIGNATURE-ALGORITHM-CLASS ::= { - ID id-dsa-with-sha1 - TYPE Dss-Parms } + ID id-dsa-with-sha1 + TYPE DSAParams } -- -- RSA Keys and Signatures diff --git a/lib/public_key/src/pubkey_cert.erl b/lib/public_key/src/pubkey_cert.erl index e704c168f1..2335a4e4b4 100644 --- a/lib/public_key/src/pubkey_cert.erl +++ b/lib/public_key/src/pubkey_cert.erl @@ -290,7 +290,7 @@ is_fixed_dh_cert(#'OTPCertificate'{tbsCertificate = %%-------------------------------------------------------------------- --spec verify_fun(#'OTPTBSCertificate'{}, {bad_cert, atom()} | {extension, #'Extension'{}}| +-spec verify_fun(#'OTPCertificate'{}, {bad_cert, atom()} | {extension, #'Extension'{}}| valid, term(), fun()) -> term(). %% %% Description: Gives the user application the opportunity handle path @@ -313,7 +313,7 @@ verify_fun(Otpcert, Result, UserState0, VerifyFun) -> {extension, #'Extension'{critical = true}} -> throw({bad_cert, unknown_critical_extension}); _ -> - UserState + UserState end end. @@ -389,10 +389,12 @@ public_key_info(PublicKeyInfo, NewPublicKeyParams = case PublicKeyParams of - 'NULL' when WorkingAlgorithm == Algorithm -> + {null, 'NULL'} when WorkingAlgorithm == Algorithm -> WorkingParams; - _ -> - PublicKeyParams + {params, Params} -> + Params; + Params -> + Params end, {Algorithm, PublicKey, NewPublicKeyParams}. diff --git a/lib/public_key/src/public_key.erl b/lib/public_key/src/public_key.erl index 902e9ad3c0..aa3018bd2d 100644 --- a/lib/public_key/src/public_key.erl +++ b/lib/public_key/src/public_key.erl @@ -528,7 +528,6 @@ path_validation([DerCert | _] = Path, {error, Reason} end. - validate(DerCert, #path_validation_state{working_issuer_name = Issuer, working_public_key = Key, working_public_key_parameters = diff --git a/lib/public_key/test/erl_make_certs.erl b/lib/public_key/test/erl_make_certs.erl index e31e5552d3..8b01ca3ad4 100644 --- a/lib/public_key/test/erl_make_certs.erl +++ b/lib/public_key/test/erl_make_certs.erl @@ -66,7 +66,7 @@ make_cert(Opts) -> %% @end %%-------------------------------------------------------------------- write_pem(Dir, FileName, {Cert, Key = {_,_,not_encrypted}}) when is_binary(Cert) -> - ok = der_to_pem(filename:join(Dir, FileName ++ ".pem"), + ok = der_to_pem(filename:join(Dir, FileName ++ ".pem"), [{'Certificate', Cert, not_encrypted}]), ok = der_to_pem(filename:join(Dir, FileName ++ "_key.pem"), [Key]). @@ -268,7 +268,7 @@ publickey(#'RSAPrivateKey'{modulus=N, publicExponent=E}) -> subjectPublicKey = Public}; publickey(#'DSAPrivateKey'{p=P, q=Q, g=G, y=Y}) -> Algo = #'PublicKeyAlgorithm'{algorithm= ?'id-dsa', - parameters=#'Dss-Parms'{p=P, q=Q, g=G}}, + parameters={params, #'Dss-Parms'{p=P, q=Q, g=G}}}, #'OTPSubjectPublicKeyInfo'{algorithm = Algo, subjectPublicKey = Y}. validity(Opts) -> @@ -290,7 +290,7 @@ sign_algorithm(#'RSAPrivateKey'{}, Opts) -> end, {Type, 'NULL'}; sign_algorithm(#'DSAPrivateKey'{p=P, q=Q, g=G}, _Opts) -> - {?'id-dsa-with-sha1', #'Dss-Parms'{p=P, q=Q, g=G}}. + {?'id-dsa-with-sha1', {params,#'Dss-Parms'{p=P, q=Q, g=G}}}. make_key(rsa, _Opts) -> %% (OBS: for testing only) diff --git a/lib/ssl/src/ssl.erl b/lib/ssl/src/ssl.erl index 8730cad127..c13dee96f1 100644 --- a/lib/ssl/src/ssl.erl +++ b/lib/ssl/src/ssl.erl @@ -190,7 +190,8 @@ transport_accept(#sslsocket{} = ListenSocket, Timeout) -> %%-------------------------------------------------------------------- -spec ssl_accept(#sslsocket{}) -> {ok, #sslsocket{}} | {error, reason()}. --spec ssl_accept(#sslsocket{}, timeout()) -> {ok, #sslsocket{}} | {error, reason()}. +-spec ssl_accept(#sslsocket{}, list() | timeout()) -> {ok, #sslsocket{}} | {error, reason()}. +-spec ssl_accept(port(), list(), timeout()) -> {ok, #sslsocket{}} | {error, reason()}. %% %% Description: Performs accept on a ssl listen socket. e.i. performs %% ssl handshake. @@ -463,11 +464,102 @@ versions() -> %%--------------------------------------------------------------- -spec renegotiate(#sslsocket{}) -> ok | {error, reason()}. %% -%% Description: +%% Description: Initiates a renegotiation. %%-------------------------------------------------------------------- renegotiate(#sslsocket{pid = Pid, fd = new_ssl}) -> ssl_connection:renegotiation(Pid). +%%--------------------------------------------------------------- +-spec format_error({error, term()}) -> list(). +%% +%% Description: Creates error string. +%%-------------------------------------------------------------------- +format_error({error, Reason}) -> + format_error(Reason); +format_error(Reason) when is_list(Reason) -> + Reason; +format_error(closed) -> + "The connection is closed"; +format_error(ecacertfile) -> + "Own CA certificate file is invalid."; +format_error(ecertfile) -> + "Own certificate file is invalid."; +format_error(ekeyfile) -> + "Own private key file is invalid."; +format_error(esslaccept) -> + "Server SSL handshake procedure between client and server failed."; +format_error(esslconnect) -> + "Client SSL handshake procedure between client and server failed."; +format_error({eoptions, Options}) -> + lists:flatten(io_lib:format("Error in options list: ~p~n", [Options])); + +%%%%%%%%%%%% START OLD SSL format_error %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +format_error(ebadsocket) -> + "Connection not found (internal error)."; +format_error(ebadstate) -> + "Connection not in connect state (internal error)."; +format_error(ebrokertype) -> + "Wrong broker type (internal error)."; +format_error(echaintoolong) -> + "The chain of certificates provided by peer is too long."; +format_error(ecipher) -> + "Own list of specified ciphers is invalid."; +format_error(ekeymismatch) -> + "Own private key does not match own certificate."; +format_error(enoissuercert) -> + "Cannot find certificate of issuer of certificate provided by peer."; +format_error(enoservercert) -> + "Attempt to do accept without having set own certificate."; +format_error(enotlistener) -> + "Attempt to accept on a non-listening socket."; +format_error(enoproxysocket) -> + "No proxy socket found (internal error or max number of file " + "descriptors exceeded)."; +format_error(enooptions) -> + "List of options is empty."; +format_error(enotstarted) -> + "The SSL application has not been started."; +format_error(eoptions) -> + "Invalid list of options."; +format_error(epeercert) -> + "Certificate provided by peer is in error."; +format_error(epeercertexpired) -> + "Certificate provided by peer has expired."; +format_error(epeercertinvalid) -> + "Certificate provided by peer is invalid."; +format_error(eselfsignedcert) -> + "Certificate provided by peer is self signed."; +format_error(esslerrssl) -> + "SSL protocol failure. Typically because of a fatal alert from peer."; +format_error(ewantconnect) -> + "Protocol wants to connect, which is not supported in this " + "version of the SSL application."; +format_error(ex509lookup) -> + "Protocol wants X.509 lookup, which is not supported in this " + "version of the SSL application."; +format_error({badcall, _Call}) -> + "Call not recognized for current mode (active or passive) and state " + "of socket."; +format_error({badcast, _Cast}) -> + "Call not recognized for current mode (active or passive) and state " + "of socket."; + +format_error({badinfo, _Info}) -> + "Call not recognized for current mode (active or passive) and state " + "of socket."; + +%%%%%%%%%%%%%%%%%% END OLD SSL format_error %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + +format_error(Error) -> + case (catch inet:format_error(Error)) of + "unkknown POSIX" ++ _ -> + no_format(Error); + {'EXIT', _} -> + no_format(Error); + Other -> + Other + end. + %%%-------------------------------------------------------------- %%% Internal functions %%%-------------------------------------------------------------------- @@ -810,92 +902,6 @@ cipher_suites(Version, Ciphers0) -> Ciphers = [ssl_cipher:openssl_suite(C) || C <- string:tokens(Ciphers0, ":")], cipher_suites(Version, Ciphers). -format_error({error, Reason}) -> - format_error(Reason); -format_error(Reason) when is_list(Reason) -> - Reason; -format_error(closed) -> - "The connection is closed"; -format_error(ecacertfile) -> - "Own CA certificate file is invalid."; -format_error(ecertfile) -> - "Own certificate file is invalid."; -format_error(ekeyfile) -> - "Own private key file is invalid."; -format_error(esslaccept) -> - "Server SSL handshake procedure between client and server failed."; -format_error(esslconnect) -> - "Client SSL handshake procedure between client and server failed."; -format_error({eoptions, Options}) -> - lists:flatten(io_lib:format("Error in options list: ~p~n", [Options])); - -%%%%%%%%%%%% START OLD SSL format_error %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -format_error(ebadsocket) -> - "Connection not found (internal error)."; -format_error(ebadstate) -> - "Connection not in connect state (internal error)."; -format_error(ebrokertype) -> - "Wrong broker type (internal error)."; -format_error(echaintoolong) -> - "The chain of certificates provided by peer is too long."; -format_error(ecipher) -> - "Own list of specified ciphers is invalid."; -format_error(ekeymismatch) -> - "Own private key does not match own certificate."; -format_error(enoissuercert) -> - "Cannot find certificate of issuer of certificate provided by peer."; -format_error(enoservercert) -> - "Attempt to do accept without having set own certificate."; -format_error(enotlistener) -> - "Attempt to accept on a non-listening socket."; -format_error(enoproxysocket) -> - "No proxy socket found (internal error or max number of file " - "descriptors exceeded)."; -format_error(enooptions) -> - "List of options is empty."; -format_error(enotstarted) -> - "The SSL application has not been started."; -format_error(eoptions) -> - "Invalid list of options."; -format_error(epeercert) -> - "Certificate provided by peer is in error."; -format_error(epeercertexpired) -> - "Certificate provided by peer has expired."; -format_error(epeercertinvalid) -> - "Certificate provided by peer is invalid."; -format_error(eselfsignedcert) -> - "Certificate provided by peer is self signed."; -format_error(esslerrssl) -> - "SSL protocol failure. Typically because of a fatal alert from peer."; -format_error(ewantconnect) -> - "Protocol wants to connect, which is not supported in this " - "version of the SSL application."; -format_error(ex509lookup) -> - "Protocol wants X.509 lookup, which is not supported in this " - "version of the SSL application."; -format_error({badcall, _Call}) -> - "Call not recognized for current mode (active or passive) and state " - "of socket."; -format_error({badcast, _Cast}) -> - "Call not recognized for current mode (active or passive) and state " - "of socket."; - -format_error({badinfo, _Info}) -> - "Call not recognized for current mode (active or passive) and state " - "of socket."; - -%%%%%%%%%%%%%%%%%% END OLD SSL format_error %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% - -format_error(Error) -> - case (catch inet:format_error(Error)) of - "unkknown POSIX" ++ _ -> - no_format(Error); - {'EXIT', _} -> - no_format(Error); - Other -> - Other - end. - no_format(Error) -> lists:flatten(io_lib:format("No format string for error: \"~p\" available.", [Error])). diff --git a/lib/ssl/src/ssl_certificate.erl b/lib/ssl/src/ssl_certificate.erl index 826cb2340c..3c7ce837e4 100644 --- a/lib/ssl/src/ssl_certificate.erl +++ b/lib/ssl/src/ssl_certificate.erl @@ -112,9 +112,10 @@ file_to_certificats(File) -> {ok, List} = ssl_manager:cache_pem_file(File), [Bin || {'Certificate', Bin, not_encrypted} <- List]. %%-------------------------------------------------------------------- --spec validate_extension(term(), #'Extension'{}, term()) -> {valid, term()} | - {fail, tuple()} | - {unknown, term()}. +-spec validate_extension(term(), #'Extension'{} | {bad_cert, atom()} | valid, + term()) -> {valid, term()} | + {fail, tuple()} | + {unknown, term()}. %% %% Description: Validates ssl/tls specific extensions %%-------------------------------------------------------------------- diff --git a/lib/ssl/src/ssl_certificate_db.erl b/lib/ssl/src/ssl_certificate_db.erl index 7d50c30d47..2a5a7f3394 100644 --- a/lib/ssl/src/ssl_certificate_db.erl +++ b/lib/ssl/src/ssl_certificate_db.erl @@ -228,4 +228,3 @@ add_certs(Cert, Ref, CertsDb) -> "it could not be correctly decoded.~n", []), error_logger:info_report(Report) end. - diff --git a/lib/ssl/src/ssl_connection.erl b/lib/ssl/src/ssl_connection.erl index c94199c336..bd1ba6978a 100644 --- a/lib/ssl/src/ssl_connection.erl +++ b/lib/ssl/src/ssl_connection.erl @@ -75,7 +75,7 @@ session, % #session{} from ssl_handshake.hrl session_cache, % session_cache_cb, % - negotiated_version, % #protocol_version{} + negotiated_version, % tls_version() supported_protocol_versions, % [atom()] client_certificate_requested = false, key_algorithm, % atom as defined by cipher_suite diff --git a/lib/ssl/src/ssl_handshake.erl b/lib/ssl/src/ssl_handshake.erl index b9b1ccb134..5b1a510034 100644 --- a/lib/ssl/src/ssl_handshake.erl +++ b/lib/ssl/src/ssl_handshake.erl @@ -276,9 +276,9 @@ client_certificate_verify(OwnCert, MasterSecret, Version, Algorithm, end. %%-------------------------------------------------------------------- -%% -spec certificate_verify(binary(), public_key_info(), tls_version(), -%% binary(), key_algo(), -%% {_, {binary(), binary()}}) -> valid | #alert{}. +-spec certificate_verify(binary(), public_key_info(), tls_version(), + binary(), key_algo(), + {_, {binary(), binary()}}) -> valid | #alert{}. %% %% Description: Checks that the certificate_verify message is valid. %%-------------------------------------------------------------------- @@ -474,6 +474,88 @@ decode_client_key(ClientKey, Type, Version) -> dec_client_key(ClientKey, key_exchange_alg(Type), Version). %%-------------------------------------------------------------------- +-spec init_hashes() ->{{binary(), binary()}, {binary(), binary()}}. + +%% +%% Description: Calls crypto hash (md5 and sha) init functions to +%% initalize the hash context. +%%-------------------------------------------------------------------- +init_hashes() -> + T = {crypto:md5_init(), crypto:sha_init()}, + {T, T}. + +%%-------------------------------------------------------------------- +-spec update_hashes({{binary(), binary()}, {binary(), binary()}}, Data ::term()) -> + {{binary(), binary()}, {binary(), binary()}}. +%% +%% Description: Calls crypto hash (md5 and sha) update functions to +%% update the hash context with Data. +%%-------------------------------------------------------------------- +update_hashes(Hashes, % special-case SSL2 client hello + <<?CLIENT_HELLO, ?UINT24(_), ?BYTE(Major), ?BYTE(Minor), + ?UINT16(CSLength), ?UINT16(0), + ?UINT16(CDLength), + CipherSuites:CSLength/binary, + ChallengeData:CDLength/binary>>) -> + update_hashes(Hashes, + <<?CLIENT_HELLO, ?BYTE(Major), ?BYTE(Minor), + ?UINT16(CSLength), ?UINT16(0), + ?UINT16(CDLength), + CipherSuites:CSLength/binary, + ChallengeData:CDLength/binary>>); +update_hashes({{MD50, SHA0}, _Prev}, Data) -> + ?DBG_HEX(Data), + {MD51, SHA1} = {crypto:md5_update(MD50, Data), + crypto:sha_update(SHA0, Data)}, + ?DBG_HEX(crypto:md5_final(MD51)), + ?DBG_HEX(crypto:sha_final(SHA1)), + {{MD51, SHA1}, {MD50, SHA0}}. + +%%-------------------------------------------------------------------- +-spec decrypt_premaster_secret(binary(), #'RSAPrivateKey'{}) -> binary(). + +%% +%% Description: Public key decryption using the private key. +%%-------------------------------------------------------------------- +decrypt_premaster_secret(Secret, RSAPrivateKey) -> + try public_key:decrypt_private(Secret, RSAPrivateKey, + [{rsa_pad, rsa_pkcs1_padding}]) + catch + _:_ -> + throw(?ALERT_REC(?FATAL, ?DECRYPTION_FAILED)) + end. + +%%-------------------------------------------------------------------- +-spec server_key_exchange_hash(rsa | dhe_rsa| dhe_dss, binary()) -> binary(). + +%% +%% Description: Calculate server key exchange hash +%%-------------------------------------------------------------------- +server_key_exchange_hash(Algorithm, Value) when Algorithm == rsa; + Algorithm == dhe_rsa -> + MD5 = crypto:md5(Value), + SHA = crypto:sha(Value), + <<MD5/binary, SHA/binary>>; + +server_key_exchange_hash(dhe_dss, Value) -> + crypto:sha(Value). + +%%-------------------------------------------------------------------- +-spec sig_alg(atom()) -> integer(). + +%% +%% Description: Translate atom representation to enum representation. +%%-------------------------------------------------------------------- +sig_alg(dh_anon) -> + ?SIGNATURE_ANONYMOUS; +sig_alg(Alg) when Alg == dhe_rsa; Alg == rsa -> + ?SIGNATURE_RSA; +sig_alg(dhe_dss) -> + ?SIGNATURE_DSA; +sig_alg(_) -> + ?NULL. + +%%-------------------------------------------------------------------- %%% Internal functions %%-------------------------------------------------------------------- get_tls_handshake_aux(<<?BYTE(Type), ?UINT24(Length), @@ -861,14 +943,6 @@ encrypted_premaster_secret(Secret, RSAPublicKey) -> throw(?ALERT_REC(?FATAL, ?HANDSHAKE_FAILURE)) end. -decrypt_premaster_secret(Secret, RSAPrivateKey) -> - try public_key:decrypt_private(Secret, RSAPrivateKey, - [{rsa_pad, rsa_pkcs1_padding}]) - catch - _:_ -> - throw(?ALERT_REC(?FATAL, ?DECRYPTION_FAILED)) - end. - %% encode/decode stream of certificate data to/from list of certificate data certs_to_list(ASN1Certs) -> certs_to_list(ASN1Certs, []). @@ -987,29 +1061,6 @@ enc_hello_extensions([#renegotiation_info{renegotiated_connection = Info} | Rest Len = InfoLen +1, enc_hello_extensions(Rest, <<?UINT16(?RENEGOTIATION_EXT), ?UINT16(Len), ?BYTE(InfoLen), Info/binary, Acc/binary>>). -init_hashes() -> - T = {crypto:md5_init(), crypto:sha_init()}, - {T, T}. - -update_hashes(Hashes, % special-case SSL2 client hello - <<?CLIENT_HELLO, ?UINT24(_), ?BYTE(Major), ?BYTE(Minor), - ?UINT16(CSLength), ?UINT16(0), - ?UINT16(CDLength), - CipherSuites:CSLength/binary, - ChallengeData:CDLength/binary>>) -> - update_hashes(Hashes, - <<?CLIENT_HELLO, ?BYTE(Major), ?BYTE(Minor), - ?UINT16(CSLength), ?UINT16(0), - ?UINT16(CDLength), - CipherSuites:CSLength/binary, - ChallengeData:CDLength/binary>>); -update_hashes({{MD50, SHA0}, _Prev}, Data) -> - ?DBG_HEX(Data), - {MD51, SHA1} = {crypto:md5_update(MD50, Data), - crypto:sha_update(SHA0, Data)}, - ?DBG_HEX(crypto:md5_final(MD51)), - ?DBG_HEX(crypto:sha_final(SHA1)), - {{MD51, SHA1}, {MD50, SHA0}}. from_3bytes(Bin3) -> from_3bytes(Bin3, []). @@ -1098,24 +1149,6 @@ calc_certificate_verify({3, N}, _, Algorithm, Hashes) when N == 1; N == 2 -> ssl_tls1:certificate_verify(Algorithm, Hashes). -server_key_exchange_hash(Algorithm, Value) when Algorithm == rsa; - Algorithm == dhe_rsa -> - MD5 = crypto:md5(Value), - SHA = crypto:sha(Value), - <<MD5/binary, SHA/binary>>; - -server_key_exchange_hash(dhe_dss, Value) -> - crypto:sha(Value). - -sig_alg(dh_anon) -> - ?SIGNATURE_ANONYMOUS; -sig_alg(Alg) when Alg == dhe_rsa; Alg == rsa -> - ?SIGNATURE_RSA; -sig_alg(dhe_dss) -> - ?SIGNATURE_DSA; -sig_alg(_) -> - ?NULL. - key_exchange_alg(rsa) -> ?KEY_EXCHANGE_RSA; key_exchange_alg(Alg) when Alg == dhe_rsa; Alg == dhe_dss; diff --git a/lib/ssl/src/ssl_manager.erl b/lib/ssl/src/ssl_manager.erl index 0116466677..3b02d96562 100644 --- a/lib/ssl/src/ssl_manager.erl +++ b/lib/ssl/src/ssl_manager.erl @@ -122,6 +122,7 @@ server_session_id(Port, SuggestedSessionId, SslOpts) -> call({server_session_id, Port, SuggestedSessionId, SslOpts}). %%-------------------------------------------------------------------- +-spec register_session(port_num(), #session{}) -> ok. -spec register_session(host(), port_num(), #session{}) -> ok. %% %% Description: Make the session available for reuse. @@ -132,6 +133,7 @@ register_session(Host, Port, Session) -> register_session(Port, Session) -> cast({register_session, Port, Session}). %%-------------------------------------------------------------------- +-spec invalidate_session(port_num(), #session{}) -> ok. -spec invalidate_session(host(), port_num(), #session{}) -> ok. %% %% Description: Make the session unavilable for reuse. diff --git a/lib/ssl/src/ssl_record.erl b/lib/ssl/src/ssl_record.erl index acd0d49c19..803baeb09c 100644 --- a/lib/ssl/src/ssl_record.erl +++ b/lib/ssl/src/ssl_record.erl @@ -497,6 +497,66 @@ decode_cipher_text(CipherText, ConnnectionStates0) -> #alert{} = Alert -> Alert end. +%%-------------------------------------------------------------------- +-spec encode_data(iolist(), tls_version(), #connection_states{}, integer()) -> + {iolist(), iolist(), #connection_states{}}. +%% +%% Description: Encodes data to send on the ssl-socket. +%%-------------------------------------------------------------------- +encode_data(Frag, Version, ConnectionStates, RenegotiateAt) + when byte_size(Frag) < (?MAX_PLAIN_TEXT_LENGTH - 2048) -> + case encode_plain_text(?APPLICATION_DATA,Version,Frag,ConnectionStates, RenegotiateAt) of + {renegotiate, Data} -> + {[], Data, ConnectionStates}; + {Msg, CS} -> + {Msg, [], CS} + end; + +encode_data(Frag, Version, ConnectionStates, RenegotiateAt) when is_binary(Frag) -> + Data = split_bin(Frag, ?MAX_PLAIN_TEXT_LENGTH - 2048), + encode_data(Data, Version, ConnectionStates, RenegotiateAt); + +encode_data(Data, Version, ConnectionStates0, RenegotiateAt) when is_list(Data) -> + {ConnectionStates, EncodedMsg, NotEncdedData} = + lists:foldl(fun(B, {CS0, Encoded, Rest}) -> + case encode_plain_text(?APPLICATION_DATA, + Version, B, CS0, RenegotiateAt) of + {renegotiate, NotEnc} -> + {CS0, Encoded, [NotEnc | Rest]}; + {Enc, CS1} -> + {CS1, [Enc | Encoded], Rest} + end + end, {ConnectionStates0, [], []}, Data), + {lists:reverse(EncodedMsg), lists:reverse(NotEncdedData), ConnectionStates}. + +%%-------------------------------------------------------------------- +-spec encode_handshake(iolist(), tls_version(), #connection_states{}) -> + {iolist(), #connection_states{}}. +%% +%% Description: Encodes a handshake message to send on the ssl-socket. +%%-------------------------------------------------------------------- +encode_handshake(Frag, Version, ConnectionStates) -> + encode_plain_text(?HANDSHAKE, Version, Frag, ConnectionStates). + +%%-------------------------------------------------------------------- +-spec encode_alert_record(#alert{}, tls_version(), #connection_states{}) -> + {iolist(), #connection_states{}}. +%% +%% Description: Encodes an alert message to send on the ssl-socket. +%%-------------------------------------------------------------------- +encode_alert_record(#alert{level = Level, description = Description}, + Version, ConnectionStates) -> + encode_plain_text(?ALERT, Version, <<?BYTE(Level), ?BYTE(Description)>>, + ConnectionStates). + +%%-------------------------------------------------------------------- +-spec encode_change_cipher_spec(tls_version(), #connection_states{}) -> + {iolist(), #connection_states{}}. +%% +%% Description: Encodes a change_cipher_spec-message to send on the ssl socket. +%%-------------------------------------------------------------------- +encode_change_cipher_spec(Version, ConnectionStates) -> + encode_plain_text(?CHANGE_CIPHER_SPEC, Version, <<1:8>>, ConnectionStates). %%-------------------------------------------------------------------- %%% Internal functions @@ -550,43 +610,6 @@ split_bin(Bin, ChunkSize, Acc) -> lists:reverse(Acc, [Bin]) end. -encode_data(Frag, Version, ConnectionStates, RenegotiateAt) - when byte_size(Frag) < (?MAX_PLAIN_TEXT_LENGTH - 2048) -> - case encode_plain_text(?APPLICATION_DATA,Version,Frag,ConnectionStates, RenegotiateAt) of - {renegotiate, Data} -> - {[], Data, ConnectionStates}; - {Msg, CS} -> - {Msg, [], CS} - end; - -encode_data(Frag, Version, ConnectionStates, RenegotiateAt) when is_binary(Frag) -> - Data = split_bin(Frag, ?MAX_PLAIN_TEXT_LENGTH - 2048), - encode_data(Data, Version, ConnectionStates, RenegotiateAt); - -encode_data(Data, Version, ConnectionStates0, RenegotiateAt) when is_list(Data) -> - {ConnectionStates, EncodedMsg, NotEncdedData} = - lists:foldl(fun(B, {CS0, Encoded, Rest}) -> - case encode_plain_text(?APPLICATION_DATA, - Version, B, CS0, RenegotiateAt) of - {renegotiate, NotEnc} -> - {CS0, Encoded, [NotEnc | Rest]}; - {Enc, CS1} -> - {CS1, [Enc | Encoded], Rest} - end - end, {ConnectionStates0, [], []}, Data), - {lists:reverse(EncodedMsg), lists:reverse(NotEncdedData), ConnectionStates}. - -encode_handshake(Frag, Version, ConnectionStates) -> - encode_plain_text(?HANDSHAKE, Version, Frag, ConnectionStates). - -encode_alert_record(#alert{level = Level, description = Description}, - Version, ConnectionStates) -> - encode_plain_text(?ALERT, Version, <<?BYTE(Level), ?BYTE(Description)>>, - ConnectionStates). - -encode_change_cipher_spec(Version, ConnectionStates) -> - encode_plain_text(?CHANGE_CIPHER_SPEC, Version, <<1:8>>, ConnectionStates). - encode_plain_text(Type, Version, Data, ConnectionStates, RenegotiateAt) -> #connection_states{current_write = #connection_state{sequence_number = Num}} = ConnectionStates, diff --git a/lib/ssl/test/erl_make_certs.erl b/lib/ssl/test/erl_make_certs.erl index f8aef55754..8b01ca3ad4 100644 --- a/lib/ssl/test/erl_make_certs.erl +++ b/lib/ssl/test/erl_make_certs.erl @@ -268,7 +268,7 @@ publickey(#'RSAPrivateKey'{modulus=N, publicExponent=E}) -> subjectPublicKey = Public}; publickey(#'DSAPrivateKey'{p=P, q=Q, g=G, y=Y}) -> Algo = #'PublicKeyAlgorithm'{algorithm= ?'id-dsa', - parameters=#'Dss-Parms'{p=P, q=Q, g=G}}, + parameters={params, #'Dss-Parms'{p=P, q=Q, g=G}}}, #'OTPSubjectPublicKeyInfo'{algorithm = Algo, subjectPublicKey = Y}. validity(Opts) -> @@ -290,7 +290,7 @@ sign_algorithm(#'RSAPrivateKey'{}, Opts) -> end, {Type, 'NULL'}; sign_algorithm(#'DSAPrivateKey'{p=P, q=Q, g=G}, _Opts) -> - {?'id-dsa-with-sha1', #'Dss-Parms'{p=P, q=Q, g=G}}. + {?'id-dsa-with-sha1', {params,#'Dss-Parms'{p=P, q=Q, g=G}}}. make_key(rsa, _Opts) -> %% (OBS: for testing only) diff --git a/lib/stdlib/doc/src/supervisor.xml b/lib/stdlib/doc/src/supervisor.xml index c696434d49..45fa0847a8 100644 --- a/lib/stdlib/doc/src/supervisor.xml +++ b/lib/stdlib/doc/src/supervisor.xml @@ -156,7 +156,7 @@ child_spec() = {Id,StartFunc,Restart,Shutdown,Type,Modules} the child process to terminate by calling <c>exit(Child,shutdown)</c> and then wait for an exit signal with reason <c>shutdown</c> back from the child process. If - no exit signal is received within the specified time, + no exit signal is received within the specified number of milliseconds, the child process is unconditionally terminated using <c>exit(Child,kill)</c>.</p> <p>If the child process is another supervisor, <c>Shutdown</c> diff --git a/lib/stdlib/vsn.mk b/lib/stdlib/vsn.mk index 1757d35160..db7954af04 100644 --- a/lib/stdlib/vsn.mk +++ b/lib/stdlib/vsn.mk @@ -1 +1 @@ -STDLIB_VSN = 1.17.1 +STDLIB_VSN = 1.17.2 diff --git a/lib/syntax_tools/src/epp_dodger.erl b/lib/syntax_tools/src/epp_dodger.erl index 6b0f2034f8..9f6f7d815e 100644 --- a/lib/syntax_tools/src/epp_dodger.erl +++ b/lib/syntax_tools/src/epp_dodger.erl @@ -809,6 +809,8 @@ tokens_to_string([{atom,_,A} | Ts]) -> io_lib:write_atom(A) ++ " " ++ tokens_to_string(Ts); tokens_to_string([{string, _, S} | Ts]) -> io_lib:write_string(S) ++ " " ++ tokens_to_string(Ts); +tokens_to_string([{char, _, C} | Ts]) -> + io_lib:write_char(C) ++ " " ++ tokens_to_string(Ts); tokens_to_string([{float, _, F} | Ts]) -> float_to_list(F) ++ " " ++ tokens_to_string(Ts); tokens_to_string([{integer, _, N} | Ts]) -> @@ -1178,7 +1178,7 @@ case "$1" in esac ;; primary) echo "Primary bootstrap is under version control since R13"; - echo "Use {prepare,update,commit}_primary if you really are"; + echo "Use update_primary if you really are"; echo "updating the primary bootstrap...";; boot) do_boot;; diff --git a/system/doc/tutorial/c_port.xmlsrc b/system/doc/tutorial/c_port.xmlsrc index 7e6034807b..b4caa07578 100644 --- a/system/doc/tutorial/c_port.xmlsrc +++ b/system/doc/tutorial/c_port.xmlsrc @@ -70,7 +70,7 @@ loop(Port) -> {call, Caller, Msg} -> Port ! {self(), {command, encode(Msg)}}, receive -\011{Port, {data, Data}} -> + {Port, {data, Data}} -> Caller ! {complex, decode(Data)} end, loop(Port) |