aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/appmon/doc/src/Makefile14
-rw-r--r--lib/appmon/doc/src/notes.xml20
-rw-r--r--lib/appmon/priv/Makefile4
-rw-r--r--lib/appmon/src/Makefile8
-rw-r--r--lib/appmon/vsn.mk2
-rw-r--r--lib/asn1/c_src/Makefile8
-rw-r--r--lib/asn1/doc/src/Makefile14
-rw-r--r--lib/asn1/doc/src/notes.xml26
-rw-r--r--lib/asn1/src/Makefile16
-rw-r--r--lib/asn1/src/asn1ct_check.erl20
-rw-r--r--lib/asn1/src/asn1ct_constructed_per.erl156
-rw-r--r--lib/asn1/src/asn1ct_gen_per.erl24
-rw-r--r--lib/asn1/src/asn1ct_gen_per_rt2ct.erl24
-rw-r--r--lib/asn1/src/asn1ct_parser2.erl6
-rw-r--r--lib/asn1/test/Makefile16
-rw-r--r--lib/asn1/test/asn1_SUITE_data/Extension-Addition-Group.asn18
-rw-r--r--lib/common_test/doc/src/Makefile22
-rw-r--r--lib/common_test/doc/src/common_test_app.xml28
-rw-r--r--lib/common_test/doc/src/notes.xml302
-rw-r--r--lib/common_test/doc/src/write_test_chapter.xml81
-rw-r--r--lib/common_test/priv/Makefile.in12
-rw-r--r--lib/common_test/src/Makefile12
-rw-r--r--lib/common_test/test/Makefile10
-rw-r--r--lib/compiler/doc/src/Makefile14
-rw-r--r--lib/compiler/doc/src/compile.xml3
-rw-r--r--lib/compiler/doc/src/notes.xml69
-rw-r--r--lib/compiler/src/Makefile8
-rw-r--r--lib/compiler/src/sys_pre_expand.erl20
-rw-r--r--lib/compiler/test/Makefile10
-rw-r--r--lib/compiler/vsn.mk2
-rw-r--r--lib/cosEvent/doc/src/Makefile14
-rw-r--r--lib/cosEvent/src/Makefile16
-rw-r--r--lib/cosEvent/test/Makefile10
-rw-r--r--lib/cosEventDomain/doc/src/Makefile14
-rw-r--r--lib/cosEventDomain/src/Makefile16
-rw-r--r--lib/cosEventDomain/test/Makefile6
-rw-r--r--lib/cosFileTransfer/doc/src/Makefile14
-rw-r--r--lib/cosFileTransfer/src/Makefile14
-rw-r--r--lib/cosFileTransfer/test/Makefile8
-rw-r--r--lib/cosNotification/doc/src/Makefile14
-rw-r--r--lib/cosNotification/src/Makefile14
-rw-r--r--lib/cosNotification/test/Makefile11
-rw-r--r--lib/cosProperty/doc/src/Makefile14
-rw-r--r--lib/cosProperty/src/Makefile14
-rw-r--r--lib/cosProperty/test/Makefile10
-rw-r--r--lib/cosTime/doc/src/Makefile14
-rw-r--r--lib/cosTime/src/Makefile14
-rw-r--r--lib/cosTime/test/Makefile10
-rw-r--r--lib/cosTransactions/doc/src/Makefile14
-rw-r--r--lib/cosTransactions/examples/Makefile6
-rw-r--r--lib/cosTransactions/src/Makefile12
-rw-r--r--lib/cosTransactions/test/Makefile10
-rw-r--r--lib/crypto/c_src/Makefile.in12
-rw-r--r--lib/crypto/c_src/crypto.c50
-rw-r--r--lib/crypto/doc/src/Makefile18
-rw-r--r--lib/crypto/doc/src/crypto.xml23
-rw-r--r--lib/crypto/src/Makefile8
-rw-r--r--lib/crypto/test/Makefile6
-rw-r--r--lib/debugger/doc/src/Makefile14
-rw-r--r--lib/debugger/doc/src/notes.xml16
-rw-r--r--lib/debugger/priv/Makefile4
-rw-r--r--lib/debugger/src/Makefile8
-rw-r--r--lib/debugger/test/Makefile10
-rw-r--r--lib/debugger/test/bs_construct_SUITE.erl8
-rw-r--r--lib/debugger/vsn.mk2
-rw-r--r--lib/dialyzer/doc/src/Makefile14
-rw-r--r--lib/dialyzer/doc/src/notes.xml15
-rw-r--r--lib/dialyzer/src/Makefile11
-rw-r--r--lib/dialyzer/src/dialyzer.hrl13
-rw-r--r--lib/dialyzer/src/dialyzer_analysis_callgraph.erl195
-rw-r--r--lib/dialyzer/src/dialyzer_behaviours.erl28
-rw-r--r--lib/dialyzer/src/dialyzer_callgraph.erl601
-rw-r--r--lib/dialyzer/src/dialyzer_cl.erl4
-rw-r--r--lib/dialyzer/src/dialyzer_cl_parse.erl14
-rw-r--r--lib/dialyzer/src/dialyzer_codeserver.erl302
-rw-r--r--lib/dialyzer/src/dialyzer_contracts.erl79
-rw-r--r--lib/dialyzer/src/dialyzer_coordinator.erl250
-rw-r--r--lib/dialyzer/src/dialyzer_dataflow.erl365
-rw-r--r--lib/dialyzer/src/dialyzer_options.erl2
-rw-r--r--lib/dialyzer/src/dialyzer_plt.erl93
-rw-r--r--lib/dialyzer/src/dialyzer_races.erl12
-rw-r--r--lib/dialyzer/src/dialyzer_succ_typings.erl460
-rw-r--r--lib/dialyzer/src/dialyzer_timing.erl133
-rw-r--r--lib/dialyzer/src/dialyzer_typesig.erl387
-rw-r--r--lib/dialyzer/src/dialyzer_utils.erl12
-rw-r--r--lib/dialyzer/src/dialyzer_worker.erl189
-rw-r--r--lib/dialyzer/test/Makefile10
-rw-r--r--lib/dialyzer/test/opaque_SUITE_data/results/queue1
-rw-r--r--lib/dialyzer/test/small_SUITE_data/results/contracts_with_subtypes31
-rw-r--r--lib/dialyzer/test/small_SUITE_data/results/port_info_test3
-rw-r--r--lib/dialyzer/test/small_SUITE_data/src/collapse_lists/a.erl9
-rw-r--r--lib/dialyzer/test/small_SUITE_data/src/collapse_lists/b.erl5
-rw-r--r--lib/dialyzer/test/small_SUITE_data/src/contracts_with_subtypes.erl267
-rw-r--r--lib/dialyzer/test/small_SUITE_data/src/deep_lc.erl14
-rw-r--r--lib/dialyzer/test/small_SUITE_data/src/port_info_test.erl6
-rw-r--r--lib/diameter/autoconf/vxworks/sed.general1
-rw-r--r--lib/diameter/doc/src/Makefile24
-rw-r--r--lib/diameter/src/Makefile18
-rw-r--r--lib/diameter/test/Makefile10
-rw-r--r--lib/edoc/doc/src/Makefile14
-rw-r--r--lib/edoc/include/Makefile4
-rw-r--r--lib/edoc/priv/Makefile6
-rw-r--r--lib/edoc/src/Makefile8
-rw-r--r--lib/edoc/test/Makefile10
-rw-r--r--lib/eldap/.gitignore4
-rw-r--r--lib/eldap/doc/src/Makefile18
-rw-r--r--lib/eldap/src/Makefile16
-rw-r--r--lib/eldap/test/Makefile12
-rw-r--r--lib/erl_docgen/doc/src/Makefile14
-rw-r--r--lib/erl_docgen/doc/src/notes.xml55
-rw-r--r--lib/erl_docgen/priv/bin/Makefile4
-rw-r--r--lib/erl_docgen/priv/css/Makefile8
-rw-r--r--lib/erl_docgen/priv/dtd/Makefile4
-rw-r--r--lib/erl_docgen/priv/dtd_html_entities/Makefile4
-rw-r--r--lib/erl_docgen/priv/dtd_man_entities/Makefile4
-rw-r--r--lib/erl_docgen/priv/images/Makefile8
-rw-r--r--lib/erl_docgen/priv/js/flipmenu/Makefile8
-rw-r--r--lib/erl_docgen/priv/xsl/Makefile4
-rw-r--r--lib/erl_docgen/priv/xsl/db_pdf.xsl2
-rw-r--r--lib/erl_docgen/src/Makefile8
-rw-r--r--lib/erl_docgen/vsn.mk2
-rw-r--r--lib/erl_interface/doc/src/Makefile18
-rw-r--r--lib/erl_interface/doc/src/notes.xml15
-rw-r--r--lib/erl_interface/src/Makefile.in50
-rw-r--r--lib/erl_interface/test/Makefile8
-rw-r--r--lib/erl_interface/test/all_SUITE_data/Makefile.src2
-rw-r--r--lib/erl_interface/test/all_SUITE_data/gccifier.c16
-rw-r--r--lib/erl_interface/test/all_SUITE_data/init_tc.erl5
-rw-r--r--lib/erl_interface/test/ei_tmo_SUITE.erl20
-rw-r--r--lib/erl_interface/test/erl_match_SUITE.erl30
-rw-r--r--lib/erl_interface/vsn.mk2
-rw-r--r--lib/et/doc/src/Makefile14
-rw-r--r--lib/et/doc/src/et_intro.xml4
-rw-r--r--lib/et/doc/src/notes.xml20
-rw-r--r--lib/et/examples/Makefile4
-rw-r--r--lib/et/src/Makefile16
-rw-r--r--lib/et/test/Makefile12
-rw-r--r--lib/et/vsn.mk2
-rw-r--r--lib/eunit/doc/src/Makefile14
-rw-r--r--lib/eunit/examples/Makefile4
-rw-r--r--lib/eunit/src/Makefile24
-rw-r--r--lib/eunit/test/Makefile4
-rw-r--r--lib/gs/contribs/bonk/Makefile16
-rw-r--r--lib/gs/contribs/cols/Makefile12
-rw-r--r--lib/gs/contribs/mandel/Makefile12
-rw-r--r--lib/gs/contribs/othello/Makefile12
-rw-r--r--lib/gs/doc/src/Makefile14
-rw-r--r--lib/gs/doc/src/notes.xml22
-rw-r--r--lib/gs/examples/Makefile8
-rw-r--r--lib/gs/src/Makefile12
-rw-r--r--lib/gs/src/gstk_generic.erl2
-rw-r--r--lib/gs/tcl/Makefile.in6
-rw-r--r--lib/gs/vsn.mk2
-rw-r--r--lib/hipe/amd64/Makefile4
-rw-r--r--lib/hipe/arm/Makefile4
-rw-r--r--lib/hipe/cerl/Makefile10
-rw-r--r--lib/hipe/cerl/cerl_hybrid_transform.erl153
-rw-r--r--lib/hipe/cerl/erl_bif_types.erl11
-rw-r--r--lib/hipe/cerl/erl_types.erl12
-rw-r--r--lib/hipe/doc/src/Makefile10
-rw-r--r--lib/hipe/doc/src/notes.xml46
-rw-r--r--lib/hipe/flow/Makefile8
-rw-r--r--lib/hipe/icode/Makefile8
-rw-r--r--lib/hipe/main/Makefile10
-rw-r--r--lib/hipe/main/hipe.app.src1
-rw-r--r--lib/hipe/main/hipe.erl7
-rw-r--r--lib/hipe/misc/Makefile8
-rw-r--r--lib/hipe/opt/Makefile4
-rw-r--r--lib/hipe/ppc/Makefile4
-rw-r--r--lib/hipe/regalloc/Makefile4
-rw-r--r--lib/hipe/rtl/Makefile8
-rw-r--r--lib/hipe/sparc/Makefile4
-rw-r--r--lib/hipe/tools/Makefile4
-rw-r--r--lib/hipe/util/Makefile8
-rw-r--r--lib/hipe/vsn.mk2
-rw-r--r--lib/hipe/x86/Makefile4
-rw-r--r--lib/ic/c_src/Makefile.in12
-rw-r--r--lib/ic/doc/src/Makefile14
-rw-r--r--lib/ic/doc/src/notes.xml18
-rw-r--r--lib/ic/examples/pre_post_condition/Makefile4
-rw-r--r--lib/ic/java_src/com/ericsson/otp/ic/Makefile8
-rw-r--r--lib/ic/src/Makefile34
-rw-r--r--lib/ic/src/ic.erl2
-rw-r--r--lib/ic/src/ic_pp.erl39
-rw-r--r--lib/ic/test/Makefile50
-rw-r--r--lib/ic/test/java_client_erl_server_SUITE.erl2
-rw-r--r--lib/inets/doc/src/Makefile14
-rw-r--r--lib/inets/examples/httpd_load_test/Makefile2
-rw-r--r--lib/inets/examples/server_root/Makefile46
-rw-r--r--lib/inets/priv/Makefile4
-rw-r--r--lib/inets/src/ftp/Makefile10
-rw-r--r--lib/inets/src/http_client/Makefile10
-rw-r--r--lib/inets/src/http_lib/Makefile10
-rw-r--r--lib/inets/src/http_server/Makefile10
-rw-r--r--lib/inets/src/inets_app/Makefile14
-rw-r--r--lib/inets/src/tftp/Makefile23
-rw-r--r--lib/inets/test/Makefile16
-rw-r--r--lib/inviso/doc/src/Makefile14
-rw-r--r--lib/inviso/src/Makefile12
-rw-r--r--lib/inviso/test/Makefile8
-rw-r--r--lib/jinterface/doc/src/Makefile18
-rw-r--r--lib/jinterface/doc/src/notes.xml33
-rw-r--r--lib/jinterface/java_src/com/ericsson/otp/erlang/Makefile12
-rw-r--r--lib/jinterface/test/Makefile6
-rw-r--r--lib/jinterface/vsn.mk2
-rw-r--r--lib/kernel/doc/src/Makefile22
-rw-r--r--lib/kernel/doc/src/gen_sctp.xml41
-rw-r--r--lib/kernel/doc/src/gen_tcp.xml57
-rw-r--r--lib/kernel/doc/src/gen_udp.xml57
-rw-r--r--lib/kernel/doc/src/inet.xml95
-rw-r--r--lib/kernel/doc/src/notes.xml127
-rw-r--r--lib/kernel/examples/Makefile4
-rw-r--r--lib/kernel/src/Makefile14
-rw-r--r--lib/kernel/src/disk_log.erl7
-rw-r--r--lib/kernel/src/disk_log.hrl4
-rw-r--r--lib/kernel/src/file.erl2
-rw-r--r--lib/kernel/src/gen_sctp.erl5
-rw-r--r--lib/kernel/src/gen_tcp.erl2
-rw-r--r--lib/kernel/src/gen_udp.erl5
-rw-r--r--lib/kernel/src/inet.erl4
-rw-r--r--lib/kernel/test/Makefile12
-rw-r--r--lib/kernel/test/bif_SUITE.erl94
-rw-r--r--lib/kernel/test/code_SUITE.erl6
-rw-r--r--lib/kernel/test/disk_log_SUITE.erl24
-rw-r--r--lib/kernel/test/gen_tcp_misc_SUITE.erl35
-rw-r--r--lib/kernel/test/init_SUITE.erl4
-rw-r--r--lib/kernel/test/interactive_shell_SUITE.erl6
-rw-r--r--lib/kernel/vsn.mk2
-rw-r--r--lib/megaco/Makefile25
-rw-r--r--lib/megaco/doc/src/Makefile18
-rw-r--r--lib/megaco/examples/meas/Makefile.in12
-rw-r--r--lib/megaco/examples/meas/megaco_codec_mstone_lib.erl5
-rw-r--r--lib/megaco/examples/simple/Makefile6
-rw-r--r--lib/megaco/src/app/Makefile16
-rw-r--r--lib/megaco/src/binary/Makefile10
-rw-r--r--lib/megaco/src/engine/Makefile27
-rw-r--r--lib/megaco/src/engine/modules.mk1
-rw-r--r--lib/megaco/src/flex/Makefile.in18
-rw-r--r--lib/megaco/src/tcp/Makefile10
-rw-r--r--lib/megaco/src/text/Makefile10
-rw-r--r--lib/megaco/src/udp/Makefile10
-rw-r--r--lib/megaco/test/Makefile8
-rw-r--r--lib/mnesia/doc/src/Makefile14
-rw-r--r--lib/mnesia/doc/src/notes.xml32
-rw-r--r--lib/mnesia/examples/Makefile10
-rw-r--r--lib/mnesia/include/Makefile4
-rw-r--r--lib/mnesia/src/Makefile8
-rw-r--r--lib/mnesia/test/Makefile38
-rw-r--r--lib/mnesia/test/mnesia_consistency_test.erl22
-rw-r--r--lib/mnesia/vsn.mk2
-rw-r--r--lib/observer/doc/src/Makefile18
-rw-r--r--lib/observer/src/Makefile28
-rw-r--r--lib/observer/src/crashdump_viewer_html.erl4
-rw-r--r--lib/observer/src/observer_app_wx.erl30
-rw-r--r--lib/observer/src/observer_pro_wx.erl21
-rw-r--r--lib/observer/src/observer_procinfo.erl26
-rw-r--r--lib/observer/src/observer_traceoptions_wx.erl8
-rw-r--r--lib/observer/src/observer_tv_table.erl2
-rw-r--r--lib/observer/src/observer_wx.erl40
-rw-r--r--lib/observer/test/Makefile6
-rw-r--r--lib/observer/test/crashdump_viewer_SUITE.erl46
-rw-r--r--lib/observer/vsn.mk2
-rw-r--r--lib/odbc/c_src/Makefile.in12
-rw-r--r--lib/odbc/doc/src/Makefile14
-rw-r--r--lib/odbc/src/Makefile12
-rw-r--r--lib/odbc/src/odbc.erl2
-rw-r--r--lib/odbc/test/Makefile4
-rw-r--r--lib/orber/COSS/CosNaming/Makefile10
-rw-r--r--lib/orber/c_src/Makefile.in24
-rw-r--r--lib/orber/doc/src/Makefile14
-rw-r--r--lib/orber/doc/src/notes.xml24
-rw-r--r--lib/orber/examples/Stack/Makefile4
-rw-r--r--lib/orber/java_src/Orber/Makefile4
-rw-r--r--lib/orber/priv/Makefile4
-rw-r--r--lib/orber/src/Makefile12
-rw-r--r--lib/orber/test/Makefile12
-rw-r--r--lib/orber/test/orber_test_lib.erl5
-rw-r--r--lib/orber/vsn.mk2
-rw-r--r--lib/os_mon/c_src/Makefile.in8
-rw-r--r--lib/os_mon/doc/src/Makefile18
-rw-r--r--lib/os_mon/doc/src/notes.xml19
-rw-r--r--lib/os_mon/mibs/Makefile16
-rw-r--r--lib/os_mon/src/Makefile10
-rw-r--r--lib/os_mon/src/disksup.erl10
-rw-r--r--lib/os_mon/src/memsup.erl2
-rw-r--r--lib/os_mon/src/os_mon.erl4
-rw-r--r--lib/os_mon/test/Makefile6
-rw-r--r--lib/os_mon/vsn.mk2
-rw-r--r--lib/otp_mibs/doc/src/Makefile14
-rw-r--r--lib/otp_mibs/mibs/Makefile16
-rw-r--r--lib/otp_mibs/src/Makefile8
-rw-r--r--lib/parsetools/doc/src/Makefile14
-rw-r--r--lib/parsetools/src/Makefile12
-rw-r--r--lib/parsetools/test/Makefile8
-rw-r--r--lib/percept/doc/src/Makefile14
-rw-r--r--lib/percept/priv/Makefile28
-rw-r--r--lib/percept/src/Makefile12
-rw-r--r--lib/percept/test/Makefile8
-rw-r--r--lib/pman/doc/src/Makefile14
-rw-r--r--lib/pman/doc/src/notes.xml20
-rw-r--r--lib/pman/priv/Makefile4
-rw-r--r--lib/pman/src/Makefile8
-rw-r--r--lib/pman/vsn.mk2
-rw-r--r--lib/public_key/asn1/Makefile12
-rw-r--r--lib/public_key/doc/src/Makefile14
-rw-r--r--lib/public_key/doc/src/notes.xml29
-rw-r--r--lib/public_key/src/Makefile12
-rw-r--r--lib/public_key/src/public_key.erl59
-rw-r--r--lib/public_key/test/Makefile12
-rw-r--r--lib/reltool/doc/src/Makefile14
-rw-r--r--lib/reltool/doc/src/notes.xml144
-rw-r--r--lib/reltool/examples/Makefile4
-rw-r--r--lib/reltool/src/Makefile10
-rw-r--r--lib/reltool/test/Makefile14
-rw-r--r--lib/reltool/vsn.mk2
-rw-r--r--lib/runtime_tools/c_src/Makefile.in8
-rw-r--r--lib/runtime_tools/doc/src/Makefile18
-rw-r--r--lib/runtime_tools/doc/src/notes.xml22
-rw-r--r--lib/runtime_tools/src/Makefile16
-rw-r--r--lib/runtime_tools/test/Makefile10
-rw-r--r--lib/runtime_tools/vsn.mk2
-rw-r--r--lib/sasl/doc/src/Makefile22
-rw-r--r--lib/sasl/doc/src/notes.xml96
-rw-r--r--lib/sasl/examples/src/Makefile8
-rw-r--r--lib/sasl/src/Makefile10
-rw-r--r--lib/sasl/test/Makefile10
-rw-r--r--lib/sasl/vsn.mk2
-rw-r--r--lib/snmp/doc/src/Makefile26
-rw-r--r--lib/snmp/examples/ex1/Makefile2
-rw-r--r--lib/snmp/examples/ex2/Makefile2
-rw-r--r--lib/snmp/mibs/Makefile.in24
-rw-r--r--lib/snmp/priv/conf/agent/Makefile6
-rw-r--r--lib/snmp/priv/conf/manager/Makefile6
-rw-r--r--lib/snmp/src/agent/Makefile14
-rw-r--r--lib/snmp/src/app/Makefile14
-rw-r--r--lib/snmp/src/compile/Makefile14
-rw-r--r--lib/snmp/src/manager/Makefile14
-rw-r--r--lib/snmp/src/misc/Makefile14
-rw-r--r--lib/snmp/test/Makefile12
-rw-r--r--lib/ssh/doc/src/Makefile14
-rw-r--r--lib/ssh/doc/src/notes.xml102
-rw-r--r--lib/ssh/examples/Makefile4
-rw-r--r--lib/ssh/src/Makefile54
-rw-r--r--lib/ssh/src/ssh.erl20
-rw-r--r--lib/ssh/src/ssh_auth.erl16
-rw-r--r--lib/ssh/src/ssh_channel.erl4
-rw-r--r--lib/ssh/src/ssh_connection.erl13
-rw-r--r--lib/ssh/src/ssh_connection_manager.erl9
-rw-r--r--lib/ssh/test/Makefile12
-rw-r--r--lib/ssh/test/ssh_basic_SUITE.erl36
-rw-r--r--lib/ssl/doc/src/Makefile18
-rw-r--r--lib/ssl/doc/src/notes.xml48
-rw-r--r--lib/ssl/doc/src/ssl.xml14
-rw-r--r--lib/ssl/examples/certs/Makefile6
-rw-r--r--lib/ssl/examples/src/Makefile8
-rw-r--r--lib/ssl/src/Makefile31
-rw-r--r--lib/ssl/src/ssl.erl36
-rw-r--r--lib/ssl/src/ssl_certificate_db.erl193
-rw-r--r--lib/ssl/src/ssl_connection.erl317
-rw-r--r--lib/ssl/src/ssl_handshake.erl44
-rw-r--r--lib/ssl/src/ssl_manager.erl202
-rw-r--r--lib/ssl/src/ssl_session.erl120
-rw-r--r--lib/ssl/src/ssl_session_cache.erl4
-rw-r--r--lib/ssl/test/Makefile10
-rw-r--r--lib/ssl/test/ssl_basic_SUITE.erl60
-rw-r--r--lib/ssl/test/ssl_dist_SUITE.erl4
-rw-r--r--lib/ssl/test/ssl_packet_SUITE.erl3
-rw-r--r--lib/ssl/test/ssl_payload_SUITE.erl1
-rw-r--r--lib/ssl/test/ssl_session_cache_SUITE.erl1
-rw-r--r--lib/ssl/test/ssl_to_openssl_SUITE.erl18
-rw-r--r--lib/stdlib/doc/src/Makefile18
-rw-r--r--lib/stdlib/doc/src/notes.xml165
-rw-r--r--lib/stdlib/examples/Makefile4
-rw-r--r--lib/stdlib/src/Makefile14
-rw-r--r--lib/stdlib/src/filelib.erl3
-rw-r--r--lib/stdlib/src/lib.erl4
-rw-r--r--lib/stdlib/test/Makefile8
-rw-r--r--lib/stdlib/test/escript_SUITE.erl2
-rw-r--r--lib/stdlib/test/ets_SUITE.erl35
-rw-r--r--lib/stdlib/test/io_proto_SUITE.erl25
-rw-r--r--lib/stdlib/test/shell_SUITE.erl12
-rw-r--r--lib/stdlib/vsn.mk2
-rw-r--r--lib/syntax_tools/doc/src/Makefile14
-rw-r--r--lib/syntax_tools/doc/src/notes.xml15
-rw-r--r--lib/syntax_tools/examples/Makefile4
-rw-r--r--lib/syntax_tools/src/Makefile8
-rw-r--r--lib/syntax_tools/test/Makefile8
-rw-r--r--lib/syntax_tools/vsn.mk2
-rw-r--r--lib/test_server/doc/src/Makefile18
-rw-r--r--lib/test_server/doc/src/notes.xml149
-rw-r--r--lib/test_server/src/Makefile20
-rw-r--r--lib/test_server/src/configure.in34
-rw-r--r--lib/test_server/src/test_server_node.erl8
-rw-r--r--lib/test_server/src/ts.erl73
-rw-r--r--lib/test_server/src/ts.hrl1
-rw-r--r--lib/test_server/src/ts_autoconf_win32.erl1
-rw-r--r--lib/test_server/src/ts_erl_config.erl69
-rw-r--r--lib/test_server/src/ts_install.erl142
-rw-r--r--lib/test_server/src/ts_install_cth.erl48
-rw-r--r--lib/test_server/src/ts_lib.erl48
-rw-r--r--lib/test_server/src/ts_make.erl12
-rw-r--r--lib/test_server/src/ts_run.erl2
-rw-r--r--lib/test_server/test/Makefile10
-rw-r--r--lib/toolbar/doc/src/Makefile14
-rw-r--r--lib/toolbar/doc/src/notes.xml20
-rw-r--r--lib/toolbar/src/Makefile8
-rw-r--r--lib/toolbar/vsn.mk2
-rw-r--r--lib/tools/c_src/Makefile.in8
-rw-r--r--lib/tools/doc/src/Makefile14
-rw-r--r--lib/tools/doc/src/eprof.xml10
-rw-r--r--lib/tools/doc/src/notes.xml25
-rw-r--r--lib/tools/emacs/Makefile8
-rw-r--r--lib/tools/emacs/erlang.el58
-rw-r--r--lib/tools/emacs/test.erl.indented38
-rw-r--r--lib/tools/emacs/test.erl.orig38
-rw-r--r--lib/tools/examples/Makefile4
-rw-r--r--lib/tools/priv/Makefile6
-rw-r--r--lib/tools/src/Makefile8
-rw-r--r--lib/tools/src/fprof.erl23
-rw-r--r--lib/tools/test/Makefile8
-rw-r--r--lib/tools/test/cover_SUITE.erl7
-rw-r--r--lib/tools/vsn.mk2
-rw-r--r--lib/tv/doc/src/Makefile14
-rw-r--r--lib/tv/doc/src/notes.xml20
-rw-r--r--lib/tv/priv/Makefile4
-rw-r--r--lib/tv/src/Makefile8
-rw-r--r--lib/tv/vsn.mk2
-rw-r--r--lib/typer/src/Makefile8
-rw-r--r--lib/typer/src/typer.erl10
-rw-r--r--lib/webtool/doc/src/Makefile18
-rw-r--r--lib/webtool/priv/Makefile16
-rw-r--r--lib/webtool/src/Makefile8
-rw-r--r--lib/wx/c_src/Makefile.in10
-rwxr-xr-xlib/wx/configure.in3
-rw-r--r--lib/wx/doc/src/Makefile20
-rw-r--r--lib/wx/doc/src/notes.xml17
-rw-r--r--lib/wx/examples/demo/Makefile2
-rw-r--r--lib/wx/examples/simple/Makefile2
-rw-r--r--lib/wx/examples/sudoku/Makefile2
-rw-r--r--lib/wx/examples/xrc/Makefile2
-rw-r--r--lib/wx/src/Makefile18
-rw-r--r--lib/wx/test/Makefile6
-rw-r--r--lib/wx/vsn.mk2
-rw-r--r--lib/xmerl/doc/src/Makefile16
-rw-r--r--lib/xmerl/doc/src/notes.xml58
-rw-r--r--lib/xmerl/src/Makefile16
-rw-r--r--lib/xmerl/src/xmerl_sax_parser_base.erlsrc400
-rw-r--r--lib/xmerl/test/Makefile24
-rw-r--r--lib/xmerl/vsn.mk2
449 files changed, 7731 insertions, 4373 deletions
diff --git a/lib/appmon/doc/src/Makefile b/lib/appmon/doc/src/Makefile
index 743f123c06..2bf560ee6b 100644
--- a/lib/appmon/doc/src/Makefile
+++ b/lib/appmon/doc/src/Makefile
@@ -107,14 +107,14 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/appmon/doc/src/notes.xml b/lib/appmon/doc/src/notes.xml
index 4e917f3d0d..04b2b0d8ba 100644
--- a/lib/appmon/doc/src/notes.xml
+++ b/lib/appmon/doc/src/notes.xml
@@ -30,6 +30,26 @@
</header>
<p>This document describes the changes made to the Appmon application.</p>
+<section><title>Appmon 2.1.14.1</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Appmon 2.1.14</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/appmon/priv/Makefile b/lib/appmon/priv/Makefile
index 9af4fbd228..8920923c98 100644
--- a/lib/appmon/priv/Makefile
+++ b/lib/appmon/priv/Makefile
@@ -57,8 +57,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(HELP_FILES) $(TOOLBAR_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(HELP_FILES) $(TOOLBAR_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/appmon/src/Makefile b/lib/appmon/src/Makefile
index 43f4f085b8..9ee7c92a4d 100644
--- a/lib/appmon/src/Makefile
+++ b/lib/appmon/src/Makefile
@@ -92,10 +92,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/appmon/vsn.mk b/lib/appmon/vsn.mk
index 047f1eadc1..0654468b42 100644
--- a/lib/appmon/vsn.mk
+++ b/lib/appmon/vsn.mk
@@ -1 +1 @@
-APPMON_VSN = 2.1.14
+APPMON_VSN = 2.1.14.1
diff --git a/lib/asn1/c_src/Makefile b/lib/asn1/c_src/Makefile
index 8c06be56f8..903cf32838 100644
--- a/lib/asn1/c_src/Makefile
+++ b/lib/asn1/c_src/Makefile
@@ -110,10 +110,10 @@ $(NIF_SHARED_OBJ_FILE): $(NIF_OBJ_FILES)
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/lib
- $(INSTALL_PROGRAM) $(NIF_SHARED_OBJ_FILE) $(RELSYSDIR)/priv/lib
- $(INSTALL_DIR) $(RELSYSDIR)/c_src
- $(INSTALL_DATA) *.c $(RELSYSDIR)/c_src
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_PROGRAM) $(NIF_SHARED_OBJ_FILE) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_src"
+ $(INSTALL_DATA) *.c "$(RELSYSDIR)/c_src"
release_docs_spec:
diff --git a/lib/asn1/doc/src/Makefile b/lib/asn1/doc/src/Makefile
index 20bd00a3b8..9ef5750353 100644
--- a/lib/asn1/doc/src/Makefile
+++ b/lib/asn1/doc/src/Makefile
@@ -119,13 +119,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/asn1/doc/src/notes.xml b/lib/asn1/doc/src/notes.xml
index 9b6c482c0a..b5422c9083 100644
--- a/lib/asn1/doc/src/notes.xml
+++ b/lib/asn1/doc/src/notes.xml
@@ -31,6 +31,32 @@
<p>This document describes the changes made to the asn1 application.</p>
+<section><title>Asn1 1.7</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ Some ASN.1 INTEGER type and SEQUENCE constructor variants
+ previously not handled by the ASN.1 compiler are now
+ correctly handled</p>
+ <p>
+ Own Id: OTP-9688</p>
+ </item>
+ <item>
+ <p>
+ An INTEGER with a value constraint where unions are used
+ e.g. X1 ::= INTEGER (1..4 | 6 | 8 | 10 | 20) is not
+ handled correctly. For PER the value is encoded in wrong
+ number of bits.</p>
+ <p>
+ Own Id: OTP-9946</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Asn1 1.6.19</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/asn1/src/Makefile b/lib/asn1/src/Makefile
index 5614cbea91..4bd49aa93b 100644
--- a/lib/asn1/src/Makefile
+++ b/lib/asn1/src/Makefile
@@ -153,16 +153,16 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(APP_SRC) $(APPUP_SRC) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(EXAMPLES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(APP_SRC) $(APPUP_SRC) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(EXAMPLES) "$(RELSYSDIR)/examples"
# there are no include files to be used by the user
-#$(INSTALL_DIR) $(RELSYSDIR)/include
-#$(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
+#$(INSTALL_DIR) "$(RELSYSDIR)/include"
+#$(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/asn1/src/asn1ct_check.erl b/lib/asn1/src/asn1ct_check.erl
index 187339fb53..494a2eddd9 100644
--- a/lib/asn1/src/asn1ct_check.erl
+++ b/lib/asn1/src/asn1ct_check.erl
@@ -5991,17 +5991,25 @@ generate_automatic_tags1([H|T],[TagNo|TagNos]) when is_record(H,'ComponentType')
type={default,'IMPLICIT'},
form= 0 }]}, % PRIMITIVE
[H#'ComponentType'{typespec=NewTs}|generate_automatic_tags1(T,[TagNo+1|TagNos])];
-generate_automatic_tags1([ExtMark|T],[_TagNo|TagNos]) -> % EXTENSIONMARK
+generate_automatic_tags1([ExtMark = #'EXTENSIONMARK'{}|T],[_TagNo|TagNos]) ->
[ExtMark | generate_automatic_tags1(T,TagNos)];
+generate_automatic_tags1([H|T],TagList) -> % ExtensionAdditionGroup etc are just ignored
+ [H | generate_automatic_tags1(T,TagList)];
generate_automatic_tags1([],_) ->
[].
-any_manual_tag([#'ComponentType'{typespec=#type{tag=[]}}|Rest]) ->
- any_manual_tag(Rest);
-any_manual_tag([#'EXTENSIONMARK'{}|Rest]) ->
- any_manual_tag(Rest);
-any_manual_tag([_|_Rest]) ->
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% Returns true if there is at least one ComponentType with a manually
+%% specified tag. No manual tag is indicated by typespec=#type{tag=[]}
+%% so we check if we find a tag =/= [] and return true in that case
+%% all other things in the componentlist like (EXTENSIONMARK,
+%% ExtensionAdditionGroup,...) except ComponentType is simply
+%% ignored/skipped
+any_manual_tag([#'ComponentType'{typespec=#type{tag=Tag}}|_Rest])
+ when Tag =/= []->
true;
+any_manual_tag([_|Rest]) ->
+ any_manual_tag(Rest);
any_manual_tag([]) ->
false.
diff --git a/lib/asn1/src/asn1ct_constructed_per.erl b/lib/asn1/src/asn1ct_constructed_per.erl
index e07680f10b..5f5138ef23 100644
--- a/lib/asn1/src/asn1ct_constructed_per.erl
+++ b/lib/asn1/src/asn1ct_constructed_per.erl
@@ -100,18 +100,26 @@ gen_encode_constructed(Erule,Typename,D) when is_record(D,type) ->
case Ext of
{ext,_,NumExt} when NumExt > 0 ->
case extgroup_pos_and_length(CompList) of
- {extgrouppos,ExtGroupPos,ExtGroupLen} ->
- Elements = make_elements(ExtGroupPos+1,
- "Val1",lists:seq(1,ExtGroupLen)),
- emit([
- {next,val}," = case [X || X <- [",Elements,
- "],X =/= asn1_NOVALUE] of",nl,
- "[] -> ",{curr,val},";",nl,
- "_ -> setelement(",{asis,ExtGroupPos+1},",",
- {curr,val},",",
- "{extaddgroup,", Elements,"})",nl,
- "end,",nl]),
- asn1ct_name:new(val);
+ {extgrouppos,[]} -> % no extenstionAdditionGroup
+ ok;
+ {extgrouppos,ExtGroupPosLenList} ->
+ ExtGroupFun =
+ fun({ExtActualGroupPos,ExtGroupVirtualPos,ExtGroupLen}) ->
+ Elements =
+ make_elements(ExtGroupVirtualPos+1,
+ "Val1",
+ lists:seq(1,ExtGroupLen)),
+ emit([
+ {next,val}," = case [X || X <- [",Elements,
+ "],X =/= asn1_NOVALUE] of",nl,
+ "[] -> ",{curr,val},";",nl,
+ "_ -> setelement(",{asis,ExtActualGroupPos+1},",",
+ {curr,val},",",
+ "{extaddgroup,", Elements,"})",nl,
+ "end,",nl]),
+ asn1ct_name:new(val)
+ end,
+ lists:foreach(ExtGroupFun,ExtGroupPosLenList);
_ -> % no extensionAdditionGroup
ok
end,
@@ -279,9 +287,9 @@ gen_decode_constructed(Erules,Typename,D) when is_record(D,type) ->
{false,false,false}
end
end,
- NewCompList = wrap_compList(CompList),
+%% NewCompList = wrap_compList(CompList),
{AccTerm,AccBytes} =
- gen_dec_components_call(Erules,Typename,NewCompList,MaybeComma2,DecObjInf,Ext,length(Optionals)),
+ gen_dec_components_call(Erules,Typename,CompList,MaybeComma2,DecObjInf,Ext,length(Optionals)),
case asn1ct_name:all(term) of
[] -> emit(MaybeComma2); % no components at all
_ -> emit({com,nl})
@@ -689,24 +697,28 @@ ext_length([],_,Acc) ->
Acc.
extgroup_pos_and_length(CompList) when is_list(CompList) ->
- noextgroup;
+ {extgrouppos,[]};
extgroup_pos_and_length({RootList,ExtList}) ->
- extgrouppos(ExtList,length(RootList)+1);
-extgroup_pos_and_length({Rl1,Ext,_Rl2}) ->
- extgrouppos(Ext,length(Rl1)+1).
-
-extgrouppos([{'ExtensionAdditionGroup',_Num}|T],Pos) ->
- extgrouppos(T,Pos,0);
-extgrouppos([_|T],Pos) ->
- extgrouppos(T,Pos+1);
-extgrouppos([],_) ->
- noextgroup.
-
-extgrouppos(['ExtensionAdditionGroupEnd'|_T],Pos,Len) ->
- {extgrouppos,Pos,Len};
-extgrouppos([_|T],Pos,Len) ->
- extgrouppos(T,Pos,Len+1).
-
+ ActualPos = length(RootList) +1,
+ %% position to get and deliver data in the record to the user
+ VirtualPos = ActualPos,
+ %% position to encode/decode the extaddgroup as an opentype sequence
+ extgrouppos(ExtList,ActualPos,VirtualPos,[]);
+extgroup_pos_and_length({RootList,ExtList,_Rl2}) ->
+ extgroup_pos_and_length({RootList,ExtList}).
+
+extgrouppos([{'ExtensionAdditionGroup',_Num}|T],ActualPos,VirtualPos,Acc) ->
+ extgrouppos(T,ActualPos,VirtualPos,0,Acc);
+extgrouppos([_|T],ActualPos,VirtualPos,Acc) ->
+ extgrouppos(T,ActualPos+1,VirtualPos+1,Acc);
+extgrouppos([],_,_,Acc) ->
+ {extgrouppos,lists:reverse(Acc)}.
+
+extgrouppos(['ExtensionAdditionGroupEnd'|T],ActualPos,VirtualPos,Len,Acc) ->
+ extgrouppos(T,ActualPos+1,VirtualPos+Len,[{ActualPos,VirtualPos,Len}|Acc]);
+extgrouppos([_|T],ActualPos,VirtualPos,Len,Acc) ->
+ extgrouppos(T,ActualPos,VirtualPos,Len+1,Acc).
+
gen_dec_extension_value(_) ->
@@ -817,19 +829,21 @@ add_textual_order1(Cs,NumIn) ->
end,
NumIn,Cs).
-gen_enc_components_call(Erule,TopType,{Root1,ExtList,Root2},MaybeComma,DynamicEnc,Ext) ->
- gen_enc_components_call(Erule,TopType,{Root1++Root2,ExtList},MaybeComma,DynamicEnc,Ext);
-gen_enc_components_call(Erule,TopType,{CompList,ExtList},MaybeComma,DynamicEnc,Ext) ->
+gen_enc_components_call(Erule,TopType,{Root,ExtList},MaybeComma,DynamicEnc,Ext) ->
+ gen_enc_components_call(Erule,TopType,{Root,ExtList,[]},MaybeComma,DynamicEnc,Ext);
+gen_enc_components_call(Erule,TopType,CL={Root,ExtList,Root2},MaybeComma,DynamicEnc,Ext) ->
%% The type has extensionmarker
- Rpos = gen_enc_components_call1(Erule,TopType,CompList,1,MaybeComma,DynamicEnc,noext),
+ Rpos = gen_enc_components_call1(Erule,TopType,Root++Root2,1,MaybeComma,DynamicEnc,noext),
case Ext of
{ext,_,ExtNum} when ExtNum > 0 ->
emit([nl,
",Extensions",nl]);
+
_ -> true
end,
%handle extensions
- NewExtList = wrap_extensionAdditionGroups(ExtList),
+ {extgrouppos,ExtGroupPosLen} = extgroup_pos_and_length(CL),
+ NewExtList = wrap_extensionAdditionGroups(ExtList,ExtGroupPosLen),
gen_enc_components_call1(Erule,TopType,NewExtList,Rpos,MaybeComma,DynamicEnc,Ext);
gen_enc_components_call(Erule,TopType, CompList, MaybeComma, DynamicEnc, Ext) ->
%% The type has no extensionmarker
@@ -938,7 +952,7 @@ gen_enc_line(Erule,TopType,Cname,Type,Element, _Pos,DynamicEnc,Ext) ->
Atype =
case Type of
#type{def=#'ObjectClassFieldType'{type=InnerType}} ->
- InnerType;
+ InnerType;
_ ->
asn1ct_gen:get_inner(Type#type.def)
end,
@@ -948,6 +962,7 @@ gen_enc_line(Erule,TopType,Cname,Type,Element, _Pos,DynamicEnc,Ext) ->
emit(["?RT_PER:encode_open_type(dummy,?RT_PER:complete("]);
_ -> true
end,
+
case Atype of
{typefield,_} ->
case DynamicEnc of
@@ -1023,20 +1038,22 @@ gen_enc_line(Erule,TopType,Cname,Type,Element, _Pos,DynamicEnc,Ext) ->
emit("))");
_ -> true
end.
-gen_dec_components_call(Erule,TopType,{Root1,ExtList,Root2},MaybeComma,DecInfObj,Ext,NumberOfOptionals) ->
- gen_dec_components_call(Erule,TopType,{Root1++Root2,ExtList},MaybeComma,DecInfObj,Ext,NumberOfOptionals);
-gen_dec_components_call(Erule,TopType,{CompList,ExtList},MaybeComma,
+gen_dec_components_call(Erule,TopType,{Root,ExtList},MaybeComma,
DecInfObj,Ext,NumberOfOptionals) ->
+ gen_dec_components_call(Erule,TopType,{Root,ExtList,[]},MaybeComma,DecInfObj,Ext,NumberOfOptionals);
+gen_dec_components_call(Erule,TopType,CL={Root1,ExtList,Root2},MaybeComma,DecInfObj,Ext,NumberOfOptionals) ->
%% The type has extensionmarker
- OptTable = create_optionality_table(CompList),
+
+ OptTable = create_optionality_table(Root1++Root2),
{Rpos,AccTerm,AccBytes} =
- gen_dec_components_call1(Erule,TopType, CompList, 1, OptTable,
+ gen_dec_components_call1(Erule,TopType, Root1++Root2, 1, OptTable,
MaybeComma,DecInfObj,noext,[],[],
NumberOfOptionals),
emit([",",nl,"{Extensions,",{next,bytes},"} = "]),
emit(["?RT_PER:getextension(Ext,",{curr,bytes},"),",nl]),
asn1ct_name:new(bytes),
- NewExtList = wrap_extensionAdditionGroups(ExtList),
+ {extgrouppos,ExtGroupPosLen} = extgroup_pos_and_length(CL),
+ NewExtList = wrap_extensionAdditionGroups(ExtList,ExtGroupPosLen),
{_Epos,AccTermE,AccBytesE} =
gen_dec_components_call1(Erule,TopType,NewExtList,Rpos, OptTable,
"",DecInfObj,Ext,[],[],NumberOfOptionals),
@@ -1233,8 +1250,7 @@ gen_dec_line(Erule,TopType,Cname,Type,Pos,DecInfObj,Ext,Prop) ->
"} = ?RT_PER:decode_open_type(",{curr,bytes},
", []),",nl]),
emit([indent(2),"case (catch ObjFun(",
- {asis,Name},
- ",",{curr,tmpterm},",telltype,",
+ {asis,Name},",",{curr,tmpterm},",telltype,",
{asis,RestFieldNames},")) of", nl]),
emit([indent(4),"{'EXIT',",{curr,reason},"} ->",nl]),
emit([indent(6),"exit({'Type not ",
@@ -1596,42 +1612,44 @@ flat_complist({Rl1,El,Rl2}) -> Rl1 ++ El ++ Rl2;
flat_complist({Rl,El}) -> Rl ++ El;
flat_complist(CompList) -> CompList.
-wrap_compList({Root1,Ext,Root2}) ->
- {Root1,wrap_extensionAdditionGroups(Ext),Root2};
-wrap_compList({Root1,Ext}) ->
- {Root1,wrap_extensionAdditionGroups(Ext)};
-wrap_compList(CompList) ->
- CompList.
+%%wrap_compList({Root1,Ext,Root2}) ->
+%% {Root1,wrap_extensionAdditionGroups(Ext),Root2};
+%%wrap_compList({Root1,Ext}) ->
+%% {Root1,wrap_extensionAdditionGroups(Ext)};
+%%wrap_compList(CompList) ->
+%% CompList.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% Will convert all componentTypes following 'ExtensionAdditionGroup'
%% up to the matching 'ExtensionAdditionGroupEnd' into one componentType
%% of type SEQUENCE with the componentTypes as components
%%
-wrap_extensionAdditionGroups(ExtCompList) ->
- wrap_extensionAdditionGroups(ExtCompList,[],0).
+wrap_extensionAdditionGroups(ExtCompList,ExtGroupPosLen) ->
+ wrap_extensionAdditionGroups(ExtCompList,ExtGroupPosLen,[],0,0).
-wrap_extensionAdditionGroups([{'ExtensionAdditionGroup',_Number}|Rest],Acc,0) ->
- {ExtGroupCompList=
- [#'ComponentType'{textual_order=TextPos}|_],
- ['ExtensionAdditionGroupEnd'|Rest2]} =
+wrap_extensionAdditionGroups([{'ExtensionAdditionGroup',_Number}|Rest],
+ [{ActualPos,_,_}|ExtGroupPosLenRest],Acc,_ExtAddGroupDiff,ExtGroupNum) ->
+ {ExtGroupCompList,['ExtensionAdditionGroupEnd'|Rest2]} =
lists:splitwith(fun(#'ComponentType'{}) -> true;
(_) -> false
end,
Rest),
- wrap_extensionAdditionGroups(Rest2,
+ wrap_extensionAdditionGroups(Rest2,ExtGroupPosLenRest,
[#'ComponentType'{
- name='ExtAddGroup', % FIXME: handles ony one ExtAddGroup
- typespec=#type{def=#'SEQUENCE'{
- extaddgroup=1,% FIXME: handles only one
+ name=list_to_atom("ExtAddGroup"++
+ integer_to_list(ExtGroupNum+1)),
+ typespec=#type{def=#'SEQUENCE'{
+ extaddgroup=ExtGroupNum+1,
components=ExtGroupCompList}},
- textual_order = TextPos,
- prop='OPTIONAL'}|Acc],length(ExtGroupCompList)-1);
-wrap_extensionAdditionGroups([H=#'ComponentType'{textual_order=Tord}|T],Acc,ExtAddGroupDiff) when is_integer(Tord) ->
- wrap_extensionAdditionGroups(T,[H#'ComponentType'{
- textual_order=Tord - ExtAddGroupDiff}|Acc],ExtAddGroupDiff);
-wrap_extensionAdditionGroups([H|T],Acc,ExtAddGroupDiff) ->
- wrap_extensionAdditionGroups(T,[H|Acc],ExtAddGroupDiff);
-wrap_extensionAdditionGroups([],Acc,_) ->
+ textual_order = ActualPos,
+ prop='OPTIONAL'}|Acc],length(ExtGroupCompList)-1,
+ ExtGroupNum+1);
+wrap_extensionAdditionGroups([H=#'ComponentType'{textual_order=Tord}|T],
+ ExtAddGrpLenPos,Acc,ExtAddGroupDiff,ExtGroupNum) when is_integer(Tord) ->
+ wrap_extensionAdditionGroups(T,ExtAddGrpLenPos,[H#'ComponentType'{
+ textual_order=Tord - ExtAddGroupDiff}|Acc],ExtAddGroupDiff,ExtGroupNum);
+wrap_extensionAdditionGroups([H|T],ExtAddGrpLenPos,Acc,ExtAddGroupDiff,ExtGroupNum) ->
+ wrap_extensionAdditionGroups(T,ExtAddGrpLenPos,[H|Acc],ExtAddGroupDiff,ExtGroupNum);
+wrap_extensionAdditionGroups([],_,Acc,_,_) ->
lists:reverse(Acc).
diff --git a/lib/asn1/src/asn1ct_gen_per.erl b/lib/asn1/src/asn1ct_gen_per.erl
index 59b4b3d261..5f42eacbdc 100644
--- a/lib/asn1/src/asn1ct_gen_per.erl
+++ b/lib/asn1/src/asn1ct_gen_per.erl
@@ -1405,19 +1405,21 @@ get_object_field(Name,ObjectFields) ->
%% have been specified within a SEQUENCE, therefore we construct a fake sequence type here
%% so that we can generate code for it
extaddgroup2sequence(ExtList) ->
- extaddgroup2sequence(ExtList,[]).
+ extaddgroup2sequence(ExtList,0,[]).
-extaddgroup2sequence([{'ExtensionAdditionGroup',Number0}|T],Acc) ->
+extaddgroup2sequence([{'ExtensionAdditionGroup',Number0}|T],ExtNum,Acc) ->
Number = case Number0 of undefined -> 1; _ -> Number0 end,
{ExtGroupComps,['ExtensionAdditionGroupEnd'|T2]} =
lists:splitwith(fun(Elem) -> is_record(Elem,'ComponentType') end,T),
- extaddgroup2sequence(T2,[#'ComponentType'{
- name='ExtAddGroup',
- typespec=#type{def=#'SEQUENCE'{
- extaddgroup=Number,
- components=ExtGroupComps}},
- prop='OPTIONAL'}|Acc]);
-extaddgroup2sequence([C|T],Acc) ->
- extaddgroup2sequence(T,[C|Acc]);
-extaddgroup2sequence([],Acc) ->
+ extaddgroup2sequence(T2,ExtNum+1,
+ [#'ComponentType'{
+ name=list_to_atom("ExtAddGroup"++
+ integer_to_list(ExtNum+1)),
+ typespec=#type{def=#'SEQUENCE'{
+ extaddgroup=Number,
+ components=ExtGroupComps}},
+ prop='OPTIONAL'}|Acc]);
+extaddgroup2sequence([C|T],ExtNum,Acc) ->
+ extaddgroup2sequence(T,ExtNum,[C|Acc]);
+extaddgroup2sequence([],_,Acc) ->
lists:reverse(Acc).
diff --git a/lib/asn1/src/asn1ct_gen_per_rt2ct.erl b/lib/asn1/src/asn1ct_gen_per_rt2ct.erl
index 4add659d79..eda0faad3c 100644
--- a/lib/asn1/src/asn1ct_gen_per_rt2ct.erl
+++ b/lib/asn1/src/asn1ct_gen_per_rt2ct.erl
@@ -1808,19 +1808,21 @@ dec_enumerated_cases([],_,_) ->
%% have been specified within a SEQUENCE, therefore we construct a fake sequence type here
%% so that we can generate code for it
extaddgroup2sequence(ExtList) ->
- extaddgroup2sequence(ExtList,[]).
+ extaddgroup2sequence(ExtList,0,[]).
-extaddgroup2sequence([{'ExtensionAdditionGroup',Number0}|T],Acc) ->
+extaddgroup2sequence([{'ExtensionAdditionGroup',Number0}|T],ExtNum,Acc) ->
Number = case Number0 of undefined -> 1; _ -> Number0 end,
{ExtGroupComps,['ExtensionAdditionGroupEnd'|T2]} =
lists:splitwith(fun(Elem) -> is_record(Elem,'ComponentType') end,T),
- extaddgroup2sequence(T2,[#'ComponentType'{
- name='ExtAddGroup',
- typespec=#type{def=#'SEQUENCE'{
- extaddgroup=Number,
- components=ExtGroupComps}},
- prop='OPTIONAL'}|Acc]);
-extaddgroup2sequence([C|T],Acc) ->
- extaddgroup2sequence(T,[C|Acc]);
-extaddgroup2sequence([],Acc) ->
+ extaddgroup2sequence(T2,ExtNum+1,
+ [#'ComponentType'{
+ name=list_to_atom("ExtAddGroup"++
+ integer_to_list(ExtNum+1)),
+ typespec=#type{def=#'SEQUENCE'{
+ extaddgroup=Number,
+ components=ExtGroupComps}},
+ prop='OPTIONAL'}|Acc]);
+extaddgroup2sequence([C|T],ExtNum,Acc) ->
+ extaddgroup2sequence(T,ExtNum,[C|Acc]);
+extaddgroup2sequence([],_,Acc) ->
lists:reverse(Acc).
diff --git a/lib/asn1/src/asn1ct_parser2.erl b/lib/asn1/src/asn1ct_parser2.erl
index 007d390a1b..7301f49085 100644
--- a/lib/asn1/src/asn1ct_parser2.erl
+++ b/lib/asn1/src/asn1ct_parser2.erl
@@ -769,9 +769,11 @@ resolve_module(_Type, Current, undefined) ->
Current;
resolve_module(Type, Current, Imports) ->
case [Mod || #'SymbolsFromModule'{symbols = S, module = Mod} <- Imports,
- #'Externaltypereference'{type = T} <- S,
+ #'Externaltypereference'{type = T} <- S,
Type == T] of
- [#'Externaltypereference'{type = Mod}] -> Mod;
+ [#'Externaltypereference'{type = Mod}|_] -> Mod;
+ %% This allows the same symbol to be imported several times
+ %% which ought to be checked elsewhere and flagged as an error
[] -> Current
end.
diff --git a/lib/asn1/test/Makefile b/lib/asn1/test/Makefile
index 1621abbec9..6e6374baf1 100644
--- a/lib/asn1/test/Makefile
+++ b/lib/asn1/test/Makefile
@@ -156,13 +156,13 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/asn1_SUITE_data
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) asn1.spec asn1.cover $(INSTALL_PROGS) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- cd asn1_SUITE_data; tar cfh $(RELSYSDIR)/asn1_SUITE_data.tar *
- cd $(RELSYSDIR)/asn1_SUITE_data; tar xf $(RELSYSDIR)/asn1_SUITE_data.tar
- rm $(RELSYSDIR)/asn1_SUITE_data.tar
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/asn1_SUITE_data"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) asn1.spec asn1.cover $(INSTALL_PROGS) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ cd asn1_SUITE_data; tar cfh "$(RELSYSDIR)/asn1_SUITE_data.tar" *
+ cd "$(RELSYSDIR)/asn1_SUITE_data"; tar xf "$(RELSYSDIR)/asn1_SUITE_data.tar"
+ rm "$(RELSYSDIR)/asn1_SUITE_data.tar"
release_docs_spec:
diff --git a/lib/asn1/test/asn1_SUITE_data/Extension-Addition-Group.asn b/lib/asn1/test/asn1_SUITE_data/Extension-Addition-Group.asn
index fc244c30a2..cacef8b922 100644
--- a/lib/asn1/test/asn1_SUITE_data/Extension-Addition-Group.asn
+++ b/lib/asn1/test/asn1_SUITE_data/Extension-Addition-Group.asn
@@ -79,4 +79,22 @@ Ax3 ::= SEQUENCE {
}
-- { a 253, b TRUE, s {sa 17, sb TRUE, sextaddgroup 11}}
+
+-- This is to test the case with more than one ExtensionAdditionGroup
+-- which did not work before
+
+AS-Config ::= SEQUENCE {
+ a INTEGER,
+ b BOOLEAN,
+ c OCTET STRING,
+ ...,
+ [[ sourceSystemInformationBlockType1Ext OCTET STRING OPTIONAL,
+ sourceOtherConfig-r9 INTEGER
+ ]],
+ [[ sourceSCellConfigList-r10 OCTET STRING OPTIONAL
+ ]]
+}
+
+
+
END
diff --git a/lib/common_test/doc/src/Makefile b/lib/common_test/doc/src/Makefile
index d9651f13b0..2ec6952710 100644
--- a/lib/common_test/doc/src/Makefile
+++ b/lib/common_test/doc/src/Makefile
@@ -158,18 +158,18 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man1
- $(INSTALL_DATA) $(MAN1DIR)/* $(RELEASE_PATH)/man/man1
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DATA) $(MAN1DIR)/* "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/common_test/doc/src/common_test_app.xml b/lib/common_test/doc/src/common_test_app.xml
index c7f6c7ce5c..6babdb93af 100644
--- a/lib/common_test/doc/src/common_test_app.xml
+++ b/lib/common_test/doc/src/common_test_app.xml
@@ -187,9 +187,13 @@
test case is allowed to execute (including <c>init_per_testcase/2</c>
and <c>end_per_testcase/2</c>). If the timetrap time is
exceeded, the test case fails with reason
- <c>timetrap_timeout</c>. If a <c>TimeFunc</c> function is specified,
- it will be called initially and must return a value on
- <c>TimeVal</c> format.</p>
+ <c>timetrap_timeout</c>. A <c>TimeFunc</c> function can be used to
+ set a new timetrap by returning a <c>TimeVal</c>. It may also be
+ used to trigger a timetrap timeout by, at some point, returning a
+ value other than a <c>TimeVal</c>. (See the
+ <seealso marker="write_test_chapter#timetraps">User's Guide</seealso>
+ for details).
+ </p>
<p>The <c>require</c> tag specifies configuration variables
that are required by test cases (and/or configuration functions)
@@ -313,9 +317,12 @@
test case is allowed to execute (including <c>init_per_testcase/2</c>
and <c>end_per_testcase/2</c>). If the timetrap time is
exceeded, the test case fails with reason
- <c>timetrap_timeout</c>. If a <c>TimeFunc</c> function is specified,
- it will be called initially and must return a value on
- <c>TimeVal</c> format.</p>
+ <c>timetrap_timeout</c>. A <c>TimeFunc</c> function can be used to
+ set a new timetrap by returning a <c>TimeVal</c>. It may also be
+ used to trigger a timetrap timeout by, at some point, returning a
+ value other than a <c>TimeVal</c>. (See the
+ <seealso marker="write_test_chapter#timetraps">User's Guide</seealso>
+ for details).</p>
<p>The <c>require</c> tag specifies configuration variables
that are required by test cases (and/or configuration functions)
@@ -494,9 +501,12 @@
exceeded, the test case fails with reason
<c>timetrap_timeout</c>. <c>init_per_testcase/2</c>
and <c>end_per_testcase/2</c> are included in the
- timetrap time. If a <c>TimeFunc</c> function is specified,
- it will be called before the test case (or <c>init_per_testcase/2</c>)
- and must return a value on <c>TimeVal</c> format.</p>
+ timetrap time. A <c>TimeFunc</c> function can be used to
+ set a new timetrap by returning a <c>TimeVal</c>. It may also be
+ used to trigger a timetrap timeout by, at some point, returning a
+ value other than a <c>TimeVal</c>. (See the
+ <seealso marker="write_test_chapter#timetraps">User's Guide</seealso>
+ for details).</p>
<p>The <c>require</c> tag specifies configuration variables
that are required by the test case (and/or <c>init/end_per_testcase/2</c>).
diff --git a/lib/common_test/doc/src/notes.xml b/lib/common_test/doc/src/notes.xml
index da0b6b2d65..050b8774ca 100644
--- a/lib/common_test/doc/src/notes.xml
+++ b/lib/common_test/doc/src/notes.xml
@@ -32,6 +32,308 @@
<file>notes.xml</file>
</header>
+<section><title>Common_Test 1.6.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Common Test adds the test suite directories to the code
+ path before executing the tests. These directories should
+ also be removed from the code path at the end of the test
+ run, which, prior to this fix, was not performed.</p>
+ <p>
+ Own Id: OTP-9595</p>
+ </item>
+ <item>
+ <p>
+ An entry is now created in the index.html file (i.e. the
+ overview file for the test run) for each repeated test
+ during a test run. This was previously not the case. Note
+ that in the top level (logdir) index file, however, only
+ the last test result is listed. For example, given the
+ test spec:
+ [{merge_tests,false},{dirs,"test1"},{dirs,"test1"}]. In
+ the index file for the test run (under
+ Logdir/ct_run.Node.Date.Time), both tests are listed. In
+ the top level index file (under Logdir), only the last
+ test is listed (one has to find the previous results
+ through the all_runs.html file).</p>
+ <p>
+ Own Id: OTP-9634 Aux Id: seq11924 </p>
+ </item>
+ <item>
+ <p>
+ After a test case timeout or abortion, the
+ end_per_testcase function executes on a new dedicated
+ process. The group leader for this process should be set
+ to the IO server for the test case, which was not done
+ properly. The result of this error was that no warnings
+ about end_per_testcase failing or timing out were ever
+ printed in the test case log. Also, help functions such
+ as e.g. test_server:stop_node/1, attempting to
+ synchronize with the IO server, would hang. The fault has
+ been corrected.</p>
+ <p>
+ Own Id: OTP-9666</p>
+ </item>
+ <item>
+ <p>
+ The ct:get_status/0 function would cause the calling
+ process to receive 'DOWN' messages if no tests were
+ running at the time of the call. This bug has been fixed.</p>
+ <p>
+ Own Id: OTP-9830 Aux Id: seq11975 </p>
+ </item>
+ <item>
+ <p>
+ A deadlock situation could occur if Common Test is
+ forwarding error_handler printouts to Test Server at the
+ same time a new test case is starting. This error has
+ been fixed.</p>
+ <p>
+ Own Id: OTP-9894</p>
+ </item>
+ <item>
+ <p>
+ A link to the ct_run program is now created, as expected,
+ in the installation bin directory (default
+ /usr/local/bin) during 'make install'.</p>
+ <p>
+ Own Id: OTP-9898</p>
+ </item>
+ <item>
+ <p>
+ Using the repeat, duration or until option with
+ ct:run_test/1, would cause an infinite loop. This has
+ been fixed.</p>
+ <p>
+ Own Id: OTP-9899</p>
+ </item>
+ <item>
+ <p>
+ Two or more test cases executing in parallel and printing
+ to screen at the same time with ct:pal/2/3 or
+ ct:print/2/3 could write into each other's "slots" and
+ create a mess of mixed strings. In order to avoid this,
+ only a single IO message is now ever sent per printout
+ call.</p>
+ <p>
+ Own Id: OTP-9900 Aux Id: OTP-9904 </p>
+ </item>
+ <item>
+ <p>
+ When a test case was killed because of a timetrap
+ timeout, the current location (suite, case and line) was
+ not printed correctly in the log files. This has been
+ corrected.</p>
+ <p>
+ Own Id: OTP-9930 Aux Id: seq12002 </p>
+ </item>
+ <item>
+ <p>
+ The wrong exit location was printed in the log file when
+ ct:fail/1 or ct_fail/2 was called.</p>
+ <p>
+ Own Id: OTP-9933 Aux Id: seq12002 </p>
+ </item>
+ <item>
+ <p>
+ Test Server and Common Test would add new error handlers
+ with each test run and fail to remove previously added
+ ones. In the case of Test Server, this would only happen
+ if SASL was not running on the test node. This has been
+ fixed.</p>
+ <p>
+ Own Id: OTP-9941 Aux Id: seq12009 </p>
+ </item>
+ <item>
+ <p>
+ If a test case process was terminated due to an exit
+ signal from a linked process, Test Server failed to
+ report the correct name of the suite and case to the
+ framework. This has been corrected.</p>
+ <p>
+ Own Id: OTP-9958 Aux Id: OTP-9855 </p>
+ </item>
+ <item>
+ <p>
+ When starting a test with ct_run and adding a directory
+ to the code path using -pa or -pz (preceding -erl_args),
+ Common Test would delete any existing directory in the
+ code path with the same base name (see
+ filename:basename/1) as the directory being added. This
+ has been fixed.</p>
+ <p>
+ Own Id: OTP-9964</p>
+ </item>
+ <item>
+ <p>
+ If passing two or more directories with the same base
+ name (see filename:basename/1) to Common Test with ct_run
+ -pa, only one of the directories would actually be added.</p>
+ <p>
+ Own Id: OTP-9975 Aux Id: seq12019 </p>
+ </item>
+ <item>
+ <p>
+ Configuration data required by the group info function
+ was deleted before the call to post_end_per_group, which
+ made it impossible for the hook function to read and use
+ the data in question. This has been fixed.</p>
+ <p>
+ Own Id: OTP-9989</p>
+ </item>
+ <item>
+ <p>
+ Disabling built-in hooks in a test specification was
+ ignored, this has now been fixed.</p>
+ <p>
+ Own Id: OTP-10009</p>
+ </item>
+ <item>
+ <p>
+ Various typographical errors corrected in documentation
+ for common_test, driver, erl_driver and windows
+ installation instructions. (Thanks to Tuncer Ayaz)</p>
+ <p>
+ Own Id: OTP-10037</p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ A new optional feature has been introduced that enables
+ Common Test to generate priv_dir directory names that are
+ unique for each test case or config function. The name of
+ the option/flag is 'create_priv_dir' and it can be set to
+ value 'auto_per_run' (which is the default, existing,
+ behaviour), or 'auto_per_tc' or 'manual_per_tc'. If
+ 'auto_per_tc' is used, Test Server creates a dedicated
+ priv_dir automatically for each test case (which can be
+ very expensive in case of many and/or repeated cases). If
+ 'manual_per_tc' is used, the user needs to create the
+ priv_dir explicitly by calling the new function
+ ct:make_priv_dir/0.</p>
+ <p>
+ Own Id: OTP-9659 Aux Id: seq11930 </p>
+ </item>
+ <item>
+ <p>
+ A column for test case group name has been added to the
+ suite overview HTML log file.</p>
+ <p>
+ Own Id: OTP-9730 Aux Id: seq11952 </p>
+ </item>
+ <item>
+ <p>
+ It is now possible to use the post_end_per_testcase CT
+ hook function to print a comment for a test case in the
+ overview log file, even if the test case gets killed by a
+ timetrap or unknown exit signal, or if the
+ end_per_testcase function times out.</p>
+ <p>
+ Own Id: OTP-9855 Aux Id: seq11979 </p>
+ </item>
+ <item>
+ <p>
+ The pre- and post CT hook functions are now always called
+ for all configuration functions, even for configuration
+ functions that are not implemented in the test suite.</p>
+ <p>
+ Own Id: OTP-9880 Aux Id: seq11993 </p>
+ </item>
+ <item>
+ <p>
+ Common Test will now print error information (with a time
+ stamp) in the test case log file immediately when a test
+ case fails. This makes it easier to see when, in time,
+ the fault actually occured, and aid the job of locating
+ relevant trace and debug printouts in the log.</p>
+ <p>
+ Own Id: OTP-9904 Aux Id: seq11985, OTP-9900 </p>
+ </item>
+ <item>
+ <p>
+ Test Server has been modified to check the SASL
+ errlog_type parameter when receiving an error logger
+ event, so that it doesn't print reports of type that the
+ user has disabled.</p>
+ <p>
+ Own Id: OTP-9955 Aux Id: seq12013 </p>
+ </item>
+ <item>
+ <p>
+ The test specification term 'skip_groups' was implemented
+ in Common Test v1.6. It was never documented however,
+ which has now been attended to. Please see the Test
+ Specifications chapter in the User's Guide for
+ information.</p>
+ <p>
+ Own Id: OTP-9972</p>
+ </item>
+ <item>
+ <p>
+ The Common Test Master has been updated to use a CSS
+ style sheet for the html log files.</p>
+ <p>
+ Own Id: OTP-9973</p>
+ </item>
+ <item>
+ <p>
+ If the init_per_group/2 and end_per_group/2 functions are
+ not implemented in the test suite, Common Test calls it's
+ own local init- and end functions - previously named
+ ct_init_per_group/2 and ct_end_per_group/2 - when a group
+ is executed. These functions have been renamed
+ init_per_group/2 and end_per_group/2 respectively. Note
+ that this may affect any user event handler identifying
+ events by the old names.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9986 Aux Id: OTP-9992 </p>
+ </item>
+ <item>
+ <p>
+ By specifying a user defined function ({M,F,A} or fun) as
+ timetrap value, either by means of an info function or by
+ calling ct:timetrap/1, it is now possible to set a
+ timetrap that will be triggered when the user function
+ returns.</p>
+ <p>
+ Own Id: OTP-9988 Aux Id: OTP-9501, seq11894 </p>
+ </item>
+ <item>
+ <p>
+ If the optional configuration functions init_per_suite/1
+ and end_per_suite/1 are not implemented in the test
+ suite, local Common Test versions of these functions are
+ called instead, and will be displayed in the overview log
+ file. Any printouts made by the pre- or
+ post_init_per_suite and pre- or post_end_per_suite hook
+ functions are saved in the log files for these functions.</p>
+ <p>
+ Own Id: OTP-9992</p>
+ </item>
+ <item>
+ <p>
+ A hook has been added to common test which outputs
+ surefire XML for usage together with CI tools such as
+ Jenkins. To enable the hook pass '-ct_hooks cth_surefire'
+ to ct_run. See the CTH documentation for more details.</p>
+ <p>
+ Own Id: OTP-9995</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Common_Test 1.6</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/common_test/doc/src/write_test_chapter.xml b/lib/common_test/doc/src/write_test_chapter.xml
index eec7628b6f..7b7e7af8ea 100644
--- a/lib/common_test/doc/src/write_test_chapter.xml
+++ b/lib/common_test/doc/src/write_test_chapter.xml
@@ -872,34 +872,63 @@
<marker id="timetraps"></marker>
<title>Timetrap timeouts</title>
<p>The default time limit for a test case is 30 minutes, unless a
- <c>timetrap</c> is specified either by the suite info function
- or a test case info function. The timetrap timeout value defined
- in <c>suite/0</c> is the value that will be used for each test case
- in the suite (as well as for the configuration functions
- <c>init_per_suite/1</c> and <c>end_per_suite</c>). A timetrap timeout
- value set with the test case info function will override the value set
- by <c>suite/0</c>, but only for that particular test case.</p>
- <p>It is also possible to set/reset a timetrap during test case (or
- configuration function) execution. This is done by calling
- <c>ct:timetrap/1</c>. This function will cancel the current timetrap
- and start a new one.</p>
+ <c>timetrap</c> is specified either by the suite-, group-,
+ or test case info function. The timetrap timeout value defined by
+ <c>suite/0</c> is the value that will be used for each test case
+ in the suite (as well as for the configuration functions
+ <c>init_per_suite/1</c>, <c>end_per_suite/1</c>, <c>init_per_group/2</c>,
+ and <c>end_per_group/2</c>). A timetrap value defined by
+ <c>group(GroupName)</c> overrides one defined by <c>suite()</c>
+ and will be used for each test case in group <c>GroupName</c>, and any
+ of its sub-groups. If a timetrap value is defined by <c>group/1</c>
+ for a sub-group, it overrides that of its higher level groups. Timetrap
+ values set by individual test cases (by means of the test case info
+ function) overrides both group- and suite- level timetraps.</p>
+
+ <p>It is also possible to dynamically set/reset a timetrap during the
+ excution of a test case, or configuration function. This is done by calling
+ <c>ct:timetrap/1</c>. This function cancels the current timetrap
+ and starts a new one (that stays active until timeout, or end of the
+ current function).</p>
+
<p>Timetrap values can be extended with a multiplier value specified at
- startup with the <c>multiply_timetraps</c> option. It is also possible
- to let Test Server decide to scale up timetrap timeout values
- automatically, e.g. if tools such as cover or trace are running during
- the test. This feature is disabled by default and can be enabled with
- the <c>scale_timetraps</c> start option.</p>
+ startup with the <c>multiply_timetraps</c> option. It is also possible
+ to let the test server decide to scale up timetrap timeout values
+ automatically, e.g. if tools such as cover or trace are running during
+ the test. This feature is disabled by default and can be enabled with
+ the <c>scale_timetraps</c> start option.</p>
+
<p>If a test case needs to suspend itself for a time that also gets
- multipled by <c>multiply_timetraps</c>, and possibly scaled up if
- <c>scale_timetraps</c> is enabled, the function <c>ct:sleep/1</c>
- may be called.</p>
- <p>A function (<c>fun</c> or <c>MFA</c>) may be specified as timetrap value
- in the suite- and test case info function, e.g:</p>
- <p><c>{timetrap,{test_utils,get_timetrap_value,[?MODULE,system_start]}}</c></p>
- <p>The function will be called initially by Common Test (before execution
- of the suite or the test case) and must return a time value such as an
- integer (millisec), or a <c>{SecMinOrHourTag,Time}</c> tuple. More
- information can be found in the <c>common_test</c> reference manual.</p>
+ multipled by <c>multiply_timetraps</c> (and possibly also scaled up if
+ <c>scale_timetraps</c> is enabled), the function <c>ct:sleep/1</c>
+ may be used (instead of e.g. <c>timer:sleep/1</c>).</p>
+
+ <p>A function (<c>fun/0</c> or <c>MFA</c>) may be specified as
+ timetrap value in the suite-, group- and test case info function, as
+ well as argument to the <c>ct:timetrap/1</c> function. Examples:</p>
+
+ <p><c>{timetrap,{my_test_utils,timetrap,[?MODULE,system_start]}}</c></p>
+ <p><c>ct:timetrap(fun() -> my_timetrap(TestCaseName, Config) end)</c></p>
+
+ <p>The user timetrap function may be used for two things:</p>
+ <list>
+ <item>To act as a timetrap - the timeout is triggered when the
+ function returns.</item>
+ <item>To return a timetrap time value (other than a function).</item>
+ </list>
+ <p>Before execution of the timetrap function (which is performed
+ on a parallel, dedicated timetrap process), Common Test cancels
+ any previously set timer for the test case or configuration function.
+ When the timetrap function returns, the timeout is triggered, <em>unless</em>
+ the return value is a valid timetrap time, such as an integer,
+ or a <c>{SecMinOrHourTag,Time}</c> tuple (see the
+ <seealso marker="common_test">common_test reference manual</seealso> for
+ details). If a time value is returned, a new timetrap is started
+ to generate a timeout after the specified time.</p>
+
+ <p>The user timetrap function may of course return a time value after a delay,
+ and if so, the effective timetrap time is the delay time <em>plus</em> the
+ returned time.</p>
</section>
<section>
diff --git a/lib/common_test/priv/Makefile.in b/lib/common_test/priv/Makefile.in
index d9033f6ef1..8be6248e17 100644
--- a/lib/common_test/priv/Makefile.in
+++ b/lib/common_test/priv/Makefile.in
@@ -85,12 +85,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
ifeq ($(XNIX),true)
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) "$(RELSYSDIR)/priv"
else
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) "$(RELSYSDIR)/priv"
endif
release_docs_spec:
@@ -125,8 +125,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(FILES) $(IMAGES) $(CSS) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/common_test/src/Makefile b/lib/common_test/src/Makefile
index 6a16c6f3af..037a686963 100644
--- a/lib/common_test/src/Makefile
+++ b/lib/common_test/src/Makefile
@@ -133,12 +133,12 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) "$(RELSYSDIR)/include"
release_tests_spec: opt
$(INSTALL_DIR) $(RELEASE_PATH)/common_test_test
diff --git a/lib/common_test/test/Makefile b/lib/common_test/test/Makefile
index 2a52f8ed74..560a0b0d5a 100644
--- a/lib/common_test/test/Makefile
+++ b/lib/common_test/test/Makefile
@@ -97,10 +97,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec:
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(COVERFILE) $(RELSYSDIR)
- $(INSTALL_DATA) common_test.spec $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) $(COVERFILE) "$(RELSYSDIR)"
+ $(INSTALL_DATA) common_test.spec "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/compiler/doc/src/Makefile b/lib/compiler/doc/src/Makefile
index ee41a7074f..308e9c4d02 100644
--- a/lib/compiler/doc/src/Makefile
+++ b/lib/compiler/doc/src/Makefile
@@ -99,14 +99,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/compiler/doc/src/compile.xml b/lib/compiler/doc/src/compile.xml
index 84e9922847..b577e5ca4f 100644
--- a/lib/compiler/doc/src/compile.xml
+++ b/lib/compiler/doc/src/compile.xml
@@ -333,7 +333,8 @@ module.beam: module.erl \
<tag><c>{d,Macro,Value}</c></tag>
<item>
<p>Defines a macro <c>Macro</c> to have the value
- <c>Value</c>. The default is <c>true</c>.</p>
+ <c>Value</c>. <c>Macro</c> is of type atom, and <c>Value</c> can be any term.
+ The default <c>Value</c> is <c>true</c>.</p>
</item>
<tag><c>{parse_transform,Module}</c></tag>
diff --git a/lib/compiler/doc/src/notes.xml b/lib/compiler/doc/src/notes.xml
index 3f53a71764..e2a921a6f2 100644
--- a/lib/compiler/doc/src/notes.xml
+++ b/lib/compiler/doc/src/notes.xml
@@ -31,6 +31,75 @@
<p>This document describes the changes made to the Compiler
application.</p>
+<section><title>Compiler 4.8.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ In rare circumstance, the compiler could crash when
+ compiling a case statement. (Thanks to Hakan Mattsson.)</p>
+ <p>
+ Own Id: OTP-9842</p>
+ </item>
+ <item>
+ <p>Calling a guard test (such as is_list/1) from the
+ top-level in a guard, would cause a compiler crash if
+ there was a local definition with the same name.
+ Corrected to reject the program with an error
+ message.</p>
+ <p>
+ Own Id: OTP-9866</p>
+ </item>
+ <item>
+ <p>Using <c>get/1</c> in a <c>try</c> block could in some
+ cases cause an internal compiler error. (Thanks to Eric
+ Merritt.)</p>
+ <p>
+ Own Id: OTP-9867</p>
+ </item>
+ <item>
+ <p>
+ An unexported on_load function would not get run if the
+ module was compiled with the <c>inline</c> option.
+ (Thanks to Yiannis Tsiouris.)</p>
+ <p>
+ Own Id: OTP-9910</p>
+ </item>
+ <item>
+ <p>
+ Fixed a discrepancy in compile_info</p>
+ <p>
+ The BEAM disassembler used the atom 'none' to signify the
+ absence of a compile_info chunk in a .beam file. This
+ clashed with the type declaration of the compile_info
+ field of a #beam_file{} record as containing a list. Now
+ [] signifies the absence of this chunk. This simplifies
+ the code and avoids a dialyzer warning.</p>
+ <p>
+ Own Id: OTP-9917</p>
+ </item>
+ <item>
+ <p>
+ Fix typo in `compile' doc: unmatched parenthesis (Thanks
+ to Ricardo Catalinas Jim�nez)</p>
+ <p>
+ Own Id: OTP-9919</p>
+ </item>
+ <item>
+ <p>In a <c>try</c>...<c>catch</c> statement that always
+ returned <c>false</c>, the compiler would remove calls to
+ BIFs that could not cause an exception (such as
+ <c>put/2</c>). Example of such code: <c>try put(K, V),
+ false catch _:_ -&gt; false end.</c></p>
+ <p>
+ Own Id: OTP-9982</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Compiler 4.8</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/compiler/src/Makefile b/lib/compiler/src/Makefile
index 3415517fff..56c45d369c 100644
--- a/lib/compiler/src/Makefile
+++ b/lib/compiler/src/Makefile
@@ -163,11 +163,11 @@ $(EBIN)/cerl_inline.beam: $(ESRC)/cerl_inline.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
$(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(EXTRA_FILES) \
- $(YRL_FILE) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(INSTALL_FILES) $(RELSYSDIR)/ebin
+ $(YRL_FILE) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(INSTALL_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/compiler/src/sys_pre_expand.erl b/lib/compiler/src/sys_pre_expand.erl
index ba9cde1de0..68bc83433e 100644
--- a/lib/compiler/src/sys_pre_expand.erl
+++ b/lib/compiler/src/sys_pre_expand.erl
@@ -42,7 +42,7 @@
compile=[], %Compile flags
attributes=[], %Attributes
callbacks=[], %Callbacks
- defined=[], %Defined functions
+ defined, %Defined functions (gb_set)
vcount=0, %Variable counter
func=[], %Current function
arity=[], %Arity for current function
@@ -83,7 +83,7 @@ module(Fs0, Opts0) ->
{Efs,St2} = expand_pmod(Tfs, St1),
%% Get the correct list of exported functions.
Exports = case member(export_all, St2#expand.compile) of
- true -> St2#expand.defined;
+ true -> gb_sets:to_list(St2#expand.defined);
false -> St2#expand.exports
end,
%% Generate all functions from stored info.
@@ -106,10 +106,11 @@ expand_pmod(Fs0, St0) ->
true ->
Ps0
end,
+ Def = gb_sets:to_list(St0#expand.defined),
{Fs1,Xs,Ds} = sys_expand_pmod:forms(Fs0, Ps,
St0#expand.exports,
- St0#expand.defined),
- St1 = St0#expand{exports=Xs, defined=Ds},
+ Def),
+ St1 = St0#expand{exports=Xs,defined=gb_sets:from_list(Ds)},
{Fs2,St2} = add_instance(Ps, Fs1, St1),
{Fs3,St3} = ensure_new(Base, Ps0, Fs2, St2),
{Fs3,St3#expand{attributes = [{abstract, 0, [true]}
@@ -159,7 +160,7 @@ add_func(Name, Args, Body, Fs, St) ->
F = {function,0,Name,A,[{clause,0,Args,[],Body}]},
NA = {Name,A},
{[F|Fs],St#expand{exports=add_element(NA, St#expand.exports),
- defined=add_element(NA, St#expand.defined)}}.
+ defined=gb_sets:add_element(NA, St#expand.defined)}}.
%% define_function(Form, State) -> State.
%% Add function to defined if form is a function.
@@ -168,7 +169,7 @@ define_functions(Forms, #expand{defined=Predef}=St) ->
Fs = foldl(fun({function,_,N,A,_Cs}, Acc) -> [{N,A}|Acc];
(_, Acc) -> Acc
end, Predef, Forms),
- St#expand{defined=ordsets:from_list(Fs)}.
+ St#expand{defined=gb_sets:from_list(Fs)}.
module_attrs(#expand{attributes=Attributes}=St) ->
Attrs = [{attribute,Line,Name,Val} || {Name,Line,Val} <- Attributes],
@@ -187,7 +188,7 @@ module_predef_func_beh_info(#expand{callbacks=Callbacks,defined=Defined,
PreDef=[{behaviour_info,1}],
PreExp=PreDef,
{[gen_beh_info(Callbacks)],
- St#expand{defined=union(from_list(PreDef), Defined),
+ St#expand{defined=gb_sets:union(gb_sets:from_list(PreDef), Defined),
exports=union(from_list(PreExp), Exports)}}.
gen_beh_info(Callbacks) ->
@@ -215,7 +216,8 @@ module_predef_funcs_mod_info(St) ->
[{clause,0,[{var,0,'X'}],[],
[{call,0,{remote,0,{atom,0,erlang},{atom,0,get_module_info}},
[{atom,0,St#expand.module},{var,0,'X'}]}]}]}],
- St#expand{defined=union(from_list(PreDef), St#expand.defined),
+ St#expand{defined=gb_sets:union(gb_sets:from_list(PreDef),
+ St#expand.defined),
exports=union(from_list(PreExp), St#expand.exports)}}.
%% forms(Forms, State) ->
@@ -721,4 +723,4 @@ imported(F, A, St) ->
end.
defined(F, A, St) ->
- ordsets:is_element({F,A}, St#expand.defined).
+ gb_sets:is_element({F,A}, St#expand.defined).
diff --git a/lib/compiler/test/Makefile b/lib/compiler/test/Makefile
index e13ad4ae90..e047166ade 100644
--- a/lib/compiler/test/Makefile
+++ b/lib/compiler/test/Makefile
@@ -154,12 +154,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) compiler.spec compiler.cover \
- $(EMAKEFILE) $(ERL_FILES) $(CORE_FILES) $(RELSYSDIR)
+ $(EMAKEFILE) $(ERL_FILES) $(CORE_FILES) "$(RELSYSDIR)"
$(INSTALL_DATA) $(NO_OPT_ERL_FILES) $(POST_OPT_ERL_FILES) \
- $(INLINE_ERL_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INLINE_ERL_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/compiler/vsn.mk b/lib/compiler/vsn.mk
index 416c2f08bb..c9c28cf9a2 100644
--- a/lib/compiler/vsn.mk
+++ b/lib/compiler/vsn.mk
@@ -1 +1 @@
-COMPILER_VSN = 4.8
+COMPILER_VSN = 4.8.1
diff --git a/lib/cosEvent/doc/src/Makefile b/lib/cosEvent/doc/src/Makefile
index 6a9b4201d7..4a0a7429e9 100644
--- a/lib/cosEvent/doc/src/Makefile
+++ b/lib/cosEvent/doc/src/Makefile
@@ -137,13 +137,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosEvent/src/Makefile b/lib/cosEvent/src/Makefile
index f8e751f218..1825beacc5 100644
--- a/lib/cosEvent/src/Makefile
+++ b/lib/cosEvent/src/Makefile
@@ -197,14 +197,14 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) ../info $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) ../info "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosEvent/test/Makefile b/lib/cosEvent/test/Makefile
index c3f07c156f..d5350d8293 100644
--- a/lib/cosEvent/test/Makefile
+++ b/lib/cosEvent/test/Makefile
@@ -141,11 +141,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
$(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
- $(RELSYSDIR)/$(IDLOUTDIR)
+ "$(RELSYSDIR)/$(IDLOUTDIR)"
diff --git a/lib/cosEventDomain/doc/src/Makefile b/lib/cosEventDomain/doc/src/Makefile
index cd159c623c..4e54b0fb55 100644
--- a/lib/cosEventDomain/doc/src/Makefile
+++ b/lib/cosEventDomain/doc/src/Makefile
@@ -131,13 +131,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosEventDomain/src/Makefile b/lib/cosEventDomain/src/Makefile
index 409cac47f1..41a31b332f 100644
--- a/lib/cosEventDomain/src/Makefile
+++ b/lib/cosEventDomain/src/Makefile
@@ -166,14 +166,14 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) ../info $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) ../info "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosEventDomain/test/Makefile b/lib/cosEventDomain/test/Makefile
index 160c8565e8..9349067eb5 100644
--- a/lib/cosEventDomain/test/Makefile
+++ b/lib/cosEventDomain/test/Makefile
@@ -98,8 +98,8 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
diff --git a/lib/cosFileTransfer/doc/src/Makefile b/lib/cosFileTransfer/doc/src/Makefile
index d9c68987e4..706dec00ce 100644
--- a/lib/cosFileTransfer/doc/src/Makefile
+++ b/lib/cosFileTransfer/doc/src/Makefile
@@ -134,13 +134,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosFileTransfer/src/Makefile b/lib/cosFileTransfer/src/Makefile
index 1d51304f6b..1bb765db73 100644
--- a/lib/cosFileTransfer/src/Makefile
+++ b/lib/cosFileTransfer/src/Makefile
@@ -176,12 +176,12 @@ $(TARGET_FILES): IDL-GENERATED
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosFileTransfer/test/Makefile b/lib/cosFileTransfer/test/Makefile
index b46fb35356..177ad7616b 100644
--- a/lib/cosFileTransfer/test/Makefile
+++ b/lib/cosFileTransfer/test/Makefile
@@ -126,8 +126,8 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
diff --git a/lib/cosNotification/doc/src/Makefile b/lib/cosNotification/doc/src/Makefile
index 5caee09ec5..d970818928 100644
--- a/lib/cosNotification/doc/src/Makefile
+++ b/lib/cosNotification/doc/src/Makefile
@@ -159,13 +159,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosNotification/src/Makefile b/lib/cosNotification/src/Makefile
index 92225c6cfd..7b8b73aa11 100644
--- a/lib/cosNotification/src/Makefile
+++ b/lib/cosNotification/src/Makefile
@@ -367,12 +367,12 @@ $(GEN_YECC_ERL_FILES) $(GEN_YECC_HRL_FILES): cosNotification_Grammar.yrl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) $(YECC_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(IDL_FILES) $(YECC_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) $(YECC_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(IDL_FILES) $(YECC_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosNotification/test/Makefile b/lib/cosNotification/test/Makefile
index f509370430..17b60a8e9f 100644
--- a/lib/cosNotification/test/Makefile
+++ b/lib/cosNotification/test/Makefile
@@ -128,6 +128,7 @@ ERL_COMPILE_FLAGS += \
$(ERL_IDL_FLAGS) \
-pa $(ERL_TOP)/lib/orber/include \
-pa $(ERL_TOP)/internal_tools/test_server/ebin \
+ -pa $(ERL_TOP)/lib/cosEvent/ebin \
-pa $(ERL_TOP)/lib/cosNotification/ebin \
-pa $(ERL_TOP)/lib/cosNotification/test/idl_output \
-pa $(ERL_TOP)/lib/cosTime/ebin \
@@ -182,11 +183,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
$(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
- $(RELSYSDIR)/$(IDLOUTDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
+ "$(RELSYSDIR)/$(IDLOUTDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
diff --git a/lib/cosProperty/doc/src/Makefile b/lib/cosProperty/doc/src/Makefile
index 50f2e06f6c..9bfacc27bd 100644
--- a/lib/cosProperty/doc/src/Makefile
+++ b/lib/cosProperty/doc/src/Makefile
@@ -136,13 +136,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosProperty/src/Makefile b/lib/cosProperty/src/Makefile
index 8060421b4e..cb2c56743c 100644
--- a/lib/cosProperty/src/Makefile
+++ b/lib/cosProperty/src/Makefile
@@ -176,12 +176,12 @@ $(TARGET_FILES): IDL-GENERATED
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosProperty/test/Makefile b/lib/cosProperty/test/Makefile
index f6e0d0dbba..d85b8a655a 100644
--- a/lib/cosProperty/test/Makefile
+++ b/lib/cosProperty/test/Makefile
@@ -120,11 +120,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
-# $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+# $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
# $(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
-# $(RELSYSDIR)/$(IDLOUTDIR)
+# "$(RELSYSDIR)/$(IDLOUTDIR)"
diff --git a/lib/cosTime/doc/src/Makefile b/lib/cosTime/doc/src/Makefile
index 4e97b07cf4..f89c022c4a 100644
--- a/lib/cosTime/doc/src/Makefile
+++ b/lib/cosTime/doc/src/Makefile
@@ -130,13 +130,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosTime/src/Makefile b/lib/cosTime/src/Makefile
index 18c25ca8f1..35f16edcef 100644
--- a/lib/cosTime/src/Makefile
+++ b/lib/cosTime/src/Makefile
@@ -195,12 +195,12 @@ $(TARGET_FILES): IDL-GENERATED
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(GEN_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosTime/test/Makefile b/lib/cosTime/test/Makefile
index a07b27eecb..ab4d140537 100644
--- a/lib/cosTime/test/Makefile
+++ b/lib/cosTime/test/Makefile
@@ -126,11 +126,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
-# $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+# $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
# $(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
-# $(RELSYSDIR)/$(IDLOUTDIR)
+# "$(RELSYSDIR)/$(IDLOUTDIR)"
diff --git a/lib/cosTransactions/doc/src/Makefile b/lib/cosTransactions/doc/src/Makefile
index 4341ec04a3..4edad9829b 100644
--- a/lib/cosTransactions/doc/src/Makefile
+++ b/lib/cosTransactions/doc/src/Makefile
@@ -134,13 +134,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/cosTransactions/examples/Makefile b/lib/cosTransactions/examples/Makefile
index 24cd12202a..0408cad75d 100644
--- a/lib/cosTransactions/examples/Makefile
+++ b/lib/cosTransactions/examples/Makefile
@@ -149,9 +149,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(ERL_FILES) $(JAVA_FILES) $(IDL_FILES) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(INETRC_EXAMPLE) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(ERL_FILES) $(JAVA_FILES) $(IDL_FILES) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(INETRC_EXAMPLE) "$(RELSYSDIR)/examples"
@tar cf - java_output | (cd $(RELSYSDIR); tar xf -)
release_docs_spec:
diff --git a/lib/cosTransactions/src/Makefile b/lib/cosTransactions/src/Makefile
index 3c799ca0ca..0922a21641 100644
--- a/lib/cosTransactions/src/Makefile
+++ b/lib/cosTransactions/src/Makefile
@@ -170,11 +170,11 @@ $(TARGET_FILES): IDL-GENERATED
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILE) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_GEN_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(GEN_ERL_FILES) $(IDL_FILE) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_GEN_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/cosTransactions/test/Makefile b/lib/cosTransactions/test/Makefile
index 0bc8c007da..80f4b6c624 100644
--- a/lib/cosTransactions/test/Makefile
+++ b/lib/cosTransactions/test/Makefile
@@ -142,11 +142,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) \
- $(COVER_FILE) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(COVER_FILE) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
$(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
- $(RELSYSDIR)/$(IDLOUTDIR)
+ "$(RELSYSDIR)/$(IDLOUTDIR)"
diff --git a/lib/crypto/c_src/Makefile.in b/lib/crypto/c_src/Makefile.in
index 285537643e..cfc9a447e0 100644
--- a/lib/crypto/c_src/Makefile.in
+++ b/lib/crypto/c_src/Makefile.in
@@ -85,7 +85,7 @@ DYNAMIC_CRYPTO_LIB=@SSL_DYNAMIC_ONLY@
ifeq ($(DYNAMIC_CRYPTO_LIB),yes)
SSL_DED_LD_RUNTIME_LIBRARY_PATH = @SSL_DED_LD_RUNTIME_LIBRARY_PATH@
-CRYPTO_LINK_LIB=$(SSL_DED_LD_RUNTIME_LIBRARY_PATH) -L$(SSL_LIBDIR) -l$(SSL_CRYPTO_LIBNAME) -l$(SSL_SSL_LIBNAME)
+CRYPTO_LINK_LIB=$(SSL_DED_LD_RUNTIME_LIBRARY_PATH) -L$(SSL_LIBDIR) -l$(SSL_CRYPTO_LIBNAME)
else
SSL_DED_LD_RUNTIME_LIBRARY_PATH=
CRYPTO_LINK_LIB=$(SSL_LIBDIR)/lib$(SSL_CRYPTO_LIBNAME).a
@@ -133,11 +133,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/obj
- $(INSTALL_DIR) $(RELSYSDIR)/priv/lib
- $(INSTALL_DATA) $(NIF_MAKEFILE) $(RELSYSDIR)/priv/obj
- $(INSTALL_PROGRAM) $(OBJS) $(RELSYSDIR)/priv/obj
- $(INSTALL_PROGRAM) $(NIF_LIB) $(RELSYSDIR)/priv/lib
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_DATA) $(NIF_MAKEFILE) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_PROGRAM) $(OBJS) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_PROGRAM) $(NIF_LIB) "$(RELSYSDIR)/priv/lib"
release_docs_spec:
diff --git a/lib/crypto/c_src/crypto.c b/lib/crypto/c_src/crypto.c
index 4dc62421d2..4be593e208 100644
--- a/lib/crypto/c_src/crypto.c
+++ b/lib/crypto/c_src/crypto.c
@@ -1456,10 +1456,37 @@ static ERL_NIF_TERM rc2_cbc_crypt(ErlNifEnv* env, int argc, const ERL_NIF_TERM a
return ret;
}
+static int get_rsa_private_key(ErlNifEnv* env, ERL_NIF_TERM key, RSA *rsa)
+{
+ /* key=[E,N,D]|[E,N,D,P1,P2,E1,E2,C] */
+ ERL_NIF_TERM head, tail;
+
+ if (!enif_get_list_cell(env, key, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->e)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->n)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->d)
+ || (!enif_is_empty_list(env, tail) &&
+ (!enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->p)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->q)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->dmp1)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->dmq1)
+ || !enif_get_list_cell(env, tail, &head, &tail)
+ || !get_bn_from_mpint(env, head, &rsa->iqmp)
+ || !enif_is_empty_list(env, tail)))) {
+ return 0;
+ }
+ return 1;
+}
+
static ERL_NIF_TERM rsa_sign_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[])
-{/* (Type,Data,Key=[E,N,D]) */
+{/* (Type,Data,Key=[E,N,D]|[E,N,D,P1,P2,E1,E2,C]) */
ErlNifBinary data_bin, ret_bin;
- ERL_NIF_TERM head, tail;
unsigned char hmacbuf[SHA_DIGEST_LENGTH];
unsigned rsa_s_len;
RSA *rsa = RSA_new();
@@ -1470,13 +1497,7 @@ static ERL_NIF_TERM rsa_sign_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM ar
else goto badarg;
if (!inspect_mpint(env,argv[1],&data_bin)
- || !enif_get_list_cell(env, argv[2], &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->e)
- || !enif_get_list_cell(env, tail, &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->n)
- || !enif_get_list_cell(env, tail, &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->d)
- || !enif_is_empty_list(env,tail)) {
+ || !get_rsa_private_key(env, argv[2], rsa)) {
badarg:
RSA_free(rsa);
return enif_make_badarg(env);
@@ -1623,20 +1644,13 @@ static ERL_NIF_TERM rsa_public_crypt(ErlNifEnv* env, int argc, const ERL_NIF_TER
}
static ERL_NIF_TERM rsa_private_crypt(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[])
-{/* (Data, PublKey=[E,N,D], Padding, IsEncrypt) */
+{/* (Data, Key=[E,N,D]|[E,N,D,P1,P2,E1,E2,C], Padding, IsEncrypt) */
ErlNifBinary data_bin, ret_bin;
- ERL_NIF_TERM head, tail;
int padding, i;
RSA* rsa = RSA_new();
if (!enif_inspect_binary(env, argv[0], &data_bin)
- || !enif_get_list_cell(env, argv[1], &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->e)
- || !enif_get_list_cell(env, tail, &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->n)
- || !enif_get_list_cell(env, tail, &head, &tail)
- || !get_bn_from_mpint(env, head, &rsa->d)
- || !enif_is_empty_list(env,tail)
+ || !get_rsa_private_key(env, argv[1], rsa)
|| !rsa_pad(argv[2], &padding)) {
RSA_free(rsa);
diff --git a/lib/crypto/doc/src/Makefile b/lib/crypto/doc/src/Makefile
index 03aaba939b..00ae70fb4a 100644
--- a/lib/crypto/doc/src/Makefile
+++ b/lib/crypto/doc/src/Makefile
@@ -100,16 +100,16 @@ clean clean_docs clean_tex:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/crypto/doc/src/crypto.xml b/lib/crypto/doc/src/crypto.xml
index 8cb893cd1c..19db6c9dd4 100644
--- a/lib/crypto/doc/src/crypto.xml
+++ b/lib/crypto/doc/src/crypto.xml
@@ -870,10 +870,15 @@ Mpint() = <![CDATA[<<ByteLen:32/integer-big, Bytes:ByteLen/binary>>]]>
<fsummary>Sign the data using rsa with the given key.</fsummary>
<type>
<v>Data = Mpint</v>
- <v>Key = [E, N, D]</v>
+ <v>Key = [E, N, D] | [E, N, D, P1, P2, E1, E2, C]</v>
<v>E, N, D = Mpint</v>
<d>Where <c>E</c> is the public exponent, <c>N</c> is public modulus and
<c>D</c> is the private exponent.</d>
+ <v>P1, P2, E1, E2, C = Mpint</v>
+ <d>The longer key format contains redundant information that will make
+ the calculation faster. <c>P1,P2</c> are first and second prime factors.
+ <c>E1,E2</c> are first and second exponents. <c>C</c> is the CRT coefficient.
+ Terminology is taken from RFC 3447.</d>
<v>DigestType = md5 | sha</v>
<d>The default <c>DigestType</c> is sha.</d>
<v>Mpint = binary()</v>
@@ -943,10 +948,15 @@ Mpint() = <![CDATA[<<ByteLen:32/integer-big, Bytes:ByteLen/binary>>]]>
<fsummary>Decrypts ChipherText using the private Key.</fsummary>
<type>
<v>ChipherText = binary()</v>
- <v>PrivateKey = [E, N, D]</v>
+ <v>PrivateKey = [E, N, D] | [E, N, D, P1, P2, E1, E2, C]</v>
<v>E, N, D = Mpint</v>
<d>Where <c>E</c> is the public exponent, <c>N</c> is public modulus and
<c>D</c> is the private exponent.</d>
+ <v>P1, P2, E1, E2, C = Mpint</v>
+ <d>The longer key format contains redundant information that will make
+ the calculation faster. <c>P1,P2</c> are first and second prime factors.
+ <c>E1,E2</c> are first and second exponents. <c>C</c> is the CRT coefficient.
+ Terminology is taken from RFC 3447.</d>
<v>Padding = rsa_pkcs1_padding | rsa_pkcs1_oaep_padding | rsa_no_padding</v>
<v>PlainText = binary()</v>
</type>
@@ -965,10 +975,15 @@ Mpint() = <![CDATA[<<ByteLen:32/integer-big, Bytes:ByteLen/binary>>]]>
<fsummary>Encrypts Msg using the private Key.</fsummary>
<type>
<v>PlainText = binary()</v>
- <v>PrivateKey = [E, N, D]</v>
- <v>E, N, D = Mpint</v>
+ <v>PrivateKey = [E, N, D] | [E, N, D, P1, P2, E1, E2, C]</v>
+ <v>E, N, D = Mpint</v>
<d>Where <c>E</c> is the public exponent, <c>N</c> is public modulus and
<c>D</c> is the private exponent.</d>
+ <v>P1, P2, E1, E2, C = Mpint</v>
+ <d>The longer key format contains redundant information that will make
+ the calculation faster. <c>P1,P2</c> are first and second prime factors.
+ <c>E1,E2</c> are first and second exponents. <c>C</c> is the CRT coefficient.
+ Terminology is taken from RFC 3447.</d>
<v>Padding = rsa_pkcs1_padding | rsa_no_padding</v>
<v>ChipherText = binary()</v>
</type>
diff --git a/lib/crypto/src/Makefile b/lib/crypto/src/Makefile
index 0e886ce8bf..ddafb9168f 100644
--- a/lib/crypto/src/Makefile
+++ b/lib/crypto/src/Makefile
@@ -83,11 +83,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) \
- $(APPUP_TARGET) $(RELSYSDIR)/ebin
+ $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/crypto/test/Makefile b/lib/crypto/test/Makefile
index 3150bd472d..ec8136b455 100644
--- a/lib/crypto/test/Makefile
+++ b/lib/crypto/test/Makefile
@@ -75,9 +75,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
release_tests_spec: $(TEST_TARGET)
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) crypto.spec crypto.cover $(RELTEST_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) crypto.spec crypto.cover $(RELTEST_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/debugger/doc/src/Makefile b/lib/debugger/doc/src/Makefile
index 1c0bbaf9d2..bc11ed7f46 100644
--- a/lib/debugger/doc/src/Makefile
+++ b/lib/debugger/doc/src/Makefile
@@ -110,12 +110,12 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- (/bin/cp -rf $(HTMLDIR) $(RELSYSDIR)/doc)
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ (/bin/cp -rf $(HTMLDIR) "$(RELSYSDIR)/doc")
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/debugger/doc/src/notes.xml b/lib/debugger/doc/src/notes.xml
index 4d8bd8ebe4..593bf715bf 100644
--- a/lib/debugger/doc/src/notes.xml
+++ b/lib/debugger/doc/src/notes.xml
@@ -32,6 +32,22 @@
<p>This document describes the changes made to the Debugger
application.</p>
+<section><title>Debugger 3.2.8</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Fixed disappearing breakpoints bug, reported by Ricardo
+ Catalinas Jim�nez.</p>
+ <p>
+ Own Id: OTP-9950</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Debugger 3.2.7</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/debugger/priv/Makefile b/lib/debugger/priv/Makefile
index 1036a5666b..2f3002331b 100644
--- a/lib/debugger/priv/Makefile
+++ b/lib/debugger/priv/Makefile
@@ -54,8 +54,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(TOOLBAR_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(TOOLBAR_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/debugger/src/Makefile b/lib/debugger/src/Makefile
index be9a2d13cb..1f9d6f2058 100644
--- a/lib/debugger/src/Makefile
+++ b/lib/debugger/src/Makefile
@@ -129,9 +129,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(TOOLBOX_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(TARGET_TOOLBOX_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(TOOLBOX_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(TARGET_TOOLBOX_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/debugger/test/Makefile b/lib/debugger/test/Makefile
index 3dfbed31ff..bf948ce8b0 100644
--- a/lib/debugger/test/Makefile
+++ b/lib/debugger/test/Makefile
@@ -98,10 +98,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) debugger.spec debugger.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) debugger.spec debugger.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/debugger/test/bs_construct_SUITE.erl b/lib/debugger/test/bs_construct_SUITE.erl
index cf943677be..e0bda7eac8 100644
--- a/lib/debugger/test/bs_construct_SUITE.erl
+++ b/lib/debugger/test/bs_construct_SUITE.erl
@@ -477,7 +477,6 @@ mem_leak(0, _) -> ok;
mem_leak(N, B) ->
?line big_bin(B, <<23>>),
?line {'EXIT',{badarg,_}} = (catch big_bin(B, bad)),
- maybe_gc(),
mem_leak(N-1, B).
big_bin(B1, B2) ->
@@ -490,13 +489,6 @@ big_bin(B1, B2) ->
make_bin(0, Acc) -> Acc;
make_bin(N, Acc) -> make_bin(N-1, <<Acc/binary,Acc/binary>>).
-maybe_gc() ->
- case erlang:system_info(heap_type) of
- shared -> erlang:garbage_collect();
- hybrid -> erlang:garbage_collect();
- private -> ok
- end.
-
-define(COF(Int0),
?line (fun(Int) ->
true = <<Int:32/float>> =:= <<(float(Int)):32/float>>,
diff --git a/lib/debugger/vsn.mk b/lib/debugger/vsn.mk
index 01ff0eb9a8..5b572f5f20 100644
--- a/lib/debugger/vsn.mk
+++ b/lib/debugger/vsn.mk
@@ -1 +1 @@
-DEBUGGER_VSN = 3.2.7
+DEBUGGER_VSN = 3.2.8
diff --git a/lib/dialyzer/doc/src/Makefile b/lib/dialyzer/doc/src/Makefile
index 45b0ffa5ff..a827281cc5 100644
--- a/lib/dialyzer/doc/src/Makefile
+++ b/lib/dialyzer/doc/src/Makefile
@@ -100,13 +100,13 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/dialyzer/doc/src/notes.xml b/lib/dialyzer/doc/src/notes.xml
index f100865b56..934cdba437 100644
--- a/lib/dialyzer/doc/src/notes.xml
+++ b/lib/dialyzer/doc/src/notes.xml
@@ -31,6 +31,21 @@
<p>This document describes the changes made to the Dialyzer
application.</p>
+<section><title>Dialyzer 2.5.1</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p> Handle <c>nowarn_unused_function</c> the same way as
+ the compiler does. </p>
+ <p>
+ Own Id: OTP-9833</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Dialyzer 2.5</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/dialyzer/src/Makefile b/lib/dialyzer/src/Makefile
index 04f3b844c4..63cc1c98f1 100644
--- a/lib/dialyzer/src/Makefile
+++ b/lib/dialyzer/src/Makefile
@@ -63,7 +63,10 @@ MODULES = \
dialyzer_plt \
dialyzer_races \
dialyzer_succ_typings \
+ dialyzer_timing \
dialyzer_typesig \
+ dialyzer_coordinator \
+ dialyzer_worker \
dialyzer_utils
HRL_FILES= dialyzer.hrl dialyzer_gui_wx.hrl
@@ -152,10 +155,10 @@ $(EBIN)/dialyzer_utils.beam: dialyzer.hrl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
$(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(EXTRA_FILES) \
- $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(INSTALL_FILES) $(RELSYSDIR)/ebin
+ "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(INSTALL_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/dialyzer/src/dialyzer.hrl b/lib/dialyzer/src/dialyzer.hrl
index 5e089d1773..1b999a7b99 100644
--- a/lib/dialyzer/src/dialyzer.hrl
+++ b/lib/dialyzer/src/dialyzer.hrl
@@ -110,6 +110,7 @@
-type label() :: non_neg_integer().
-type rep_mode() :: 'quiet' | 'normal' | 'verbose'.
-type start_from() :: 'byte_code' | 'src_code'.
+-type mfa_or_funlbl() :: label() | mfa().
%%--------------------------------------------------------------------
%% Record declarations used by various files
@@ -126,11 +127,14 @@
use_contracts = true :: boolean(),
race_detection = false :: boolean(),
behaviours_chk = false :: boolean(),
+ timing = false :: boolean() | 'debug',
+ timing_server :: dialyzer_timing:timing_server(),
callgraph_file = "" :: file:filename()}).
-record(options, {files = [] :: [file:filename()],
files_rec = [] :: [file:filename()],
analysis_type = succ_typings :: anal_type1(),
+ timing = false :: boolean() | 'debug',
defines = [] :: [dial_define()],
from = byte_code :: start_from(),
get_warnings = maybe :: boolean() | 'maybe',
@@ -152,3 +156,12 @@
forms = [] :: [{_, _}]}).
%%--------------------------------------------------------------------
+
+-define(timing(Server, Msg, Var, Expr),
+ begin
+ dialyzer_timing:start_stamp(Server, Msg),
+ Var = Expr,
+ dialyzer_timing:end_stamp(Server),
+ Var
+ end).
+-define(timing(Server, Msg, Expr),?timing(Server, Msg, _T, Expr)).
diff --git a/lib/dialyzer/src/dialyzer_analysis_callgraph.erl b/lib/dialyzer/src/dialyzer_analysis_callgraph.erl
index 2c4622155a..3bbde12481 100644
--- a/lib/dialyzer/src/dialyzer_analysis_callgraph.erl
+++ b/lib/dialyzer/src/dialyzer_analysis_callgraph.erl
@@ -30,6 +30,15 @@
-export([start/3]).
+-export([compile_init_result/0,
+ add_to_result/4,
+ start_compilation/2,
+ continue_compilation/2]).
+
+-export_type([compile_init_data/0,
+ one_file_result/0,
+ compile_result/0]).
+
-include("dialyzer.hrl").
-record(analysis_state,
@@ -43,7 +52,8 @@
parent :: pid(),
plt :: dialyzer_plt:plt(),
start_from = byte_code :: start_from(),
- use_contracts = true :: boolean()
+ use_contracts = true :: boolean(),
+ timing_server :: dialyzer_timing:timing_server()
}).
-record(server_state, {parent :: pid(), legal_warnings :: [dial_warn_tag()]}).
@@ -55,12 +65,15 @@
-spec start(pid(), [dial_warn_tag()], #analysis{}) -> 'ok'.
start(Parent, LegalWarnings, Analysis) ->
+ TimingServer = dialyzer_timing:init(Analysis#analysis.timing),
RacesOn = ordsets:is_element(?WARN_RACE_CONDITION, LegalWarnings),
- Analysis0 = Analysis#analysis{race_detection = RacesOn},
+ Analysis0 =
+ Analysis#analysis{race_detection = RacesOn, timing_server = TimingServer},
Analysis1 = expand_files(Analysis0),
Analysis2 = run_analysis(Analysis1),
State = #server_state{parent = Parent, legal_warnings = LegalWarnings},
- loop(State, Analysis2, none).
+ loop(State, Analysis2, none),
+ dialyzer_timing:stop(TimingServer).
run_analysis(Analysis) ->
Self = self(),
@@ -122,7 +135,8 @@ analysis_start(Parent, Analysis) ->
plt = Plt,
parent = Parent,
start_from = Analysis#analysis.start_from,
- use_contracts = Analysis#analysis.use_contracts
+ use_contracts = Analysis#analysis.use_contracts,
+ timing_server = Analysis#analysis.timing_server
},
Files = ordsets:from_list(Analysis#analysis.files),
{Callgraph, NoWarn, TmpCServer0} = compile_and_store(Files, State),
@@ -146,7 +160,8 @@ analysis_start(Parent, Analysis) ->
dialyzer_codeserver:insert_temp_exported_types(MergedExpTypes,
TmpCServer1),
TmpCServer3 = dialyzer_utils:process_record_remote_types(TmpCServer2),
- dialyzer_contracts:process_contract_remote_types(TmpCServer3)
+ ?timing(State#analysis_state.timing_server, "remote",
+ dialyzer_contracts:process_contract_remote_types(TmpCServer3))
catch
throw:{error, _ErrorMsg} = Error -> exit(Error)
end,
@@ -174,72 +189,66 @@ analysis_start(Parent, Analysis) ->
send_codeserver_plt(Parent, CServer, State3#analysis_state.plt),
send_analysis_done(Parent, Plt2, State3#analysis_state.doc_plt).
-analyze_callgraph(Callgraph, State) ->
- Codeserver = State#analysis_state.codeserver,
- Parent = State#analysis_state.parent,
- DocPlt = State#analysis_state.doc_plt,
+analyze_callgraph(Callgraph, #analysis_state{codeserver = Codeserver,
+ doc_plt = DocPlt,
+ timing_server = TimingServer,
+ parent = Parent} = State) ->
Plt = dialyzer_plt:insert_callbacks(State#analysis_state.plt, Codeserver),
- Callgraph1 = dialyzer_callgraph:finalize(Callgraph),
{NewPlt, NewDocPlt} =
case State#analysis_state.analysis_type of
plt_build ->
- {dialyzer_succ_typings:analyze_callgraph(Callgraph1, Plt,
- Codeserver, Parent),
- DocPlt};
+ NewPlt0 =
+ dialyzer_succ_typings:analyze_callgraph(Callgraph, Plt, Codeserver,
+ TimingServer, Parent),
+ {NewPlt0, DocPlt};
succ_typings ->
NoWarn = State#analysis_state.no_warn_unused,
{Warnings, NewPlt0, NewDocPlt0} =
- dialyzer_succ_typings:get_warnings(Callgraph1, Plt, DocPlt,
- Codeserver, NoWarn, Parent),
+ dialyzer_succ_typings:get_warnings(Callgraph, Plt, DocPlt, Codeserver,
+ NoWarn, TimingServer, Parent),
send_warnings(State#analysis_state.parent, Warnings),
{NewPlt0, NewDocPlt0}
end,
- dialyzer_callgraph:delete(Callgraph1),
+ dialyzer_callgraph:delete(Callgraph),
State#analysis_state{plt = NewPlt, doc_plt = NewDocPlt}.
%%--------------------------------------------------------------------
%% Build the callgraph and fill the codeserver.
%%--------------------------------------------------------------------
+-record(compile_init,{
+ callgraph :: dialyzer_callgraph:callgraph(),
+ codeserver :: dialyzer_codeserver:codeserver(),
+ defines = [] :: [dial_define()],
+ include_dirs = [] :: [file:filename()],
+ start_from = byte_code :: start_from(),
+ use_contracts = true :: boolean()
+ }).
+
+make_compile_init(#analysis_state{codeserver = Codeserver,
+ defines = Defs,
+ include_dirs = Dirs,
+ use_contracts = UseContracts,
+ start_from = StartFrom}, Callgraph) ->
+ #compile_init{callgraph = Callgraph,
+ codeserver = Codeserver,
+ defines = [{d, Macro, Val} || {Macro, Val} <- Defs],
+ include_dirs = [{i, D} || D <- Dirs],
+ use_contracts = UseContracts,
+ start_from = StartFrom}.
+
compile_and_store(Files, #analysis_state{codeserver = CServer,
- defines = Defs,
- include_dirs = Dirs,
- parent = Parent,
- use_contracts = UseContracts,
- start_from = StartFrom
- } = State) ->
+ timing_server = Timing,
+ parent = Parent} = State) ->
send_log(Parent, "Reading files and computing callgraph... "),
{T1, _} = statistics(runtime),
- Includes = [{i, D} || D <- Dirs],
- Defines = [{d, Macro, Val} || {Macro, Val} <- Defs],
Callgraph = dialyzer_callgraph:new(),
- Fun = case StartFrom of
- src_code ->
- fun(File, {TmpCG, TmpCServer, TmpFailed, TmpNoWarn, TmpMods}) ->
- case compile_src(File, Includes, Defines, TmpCG,
- TmpCServer, UseContracts) of
- {error, Reason} ->
- {TmpCG, TmpCServer, [{File, Reason}|TmpFailed], TmpNoWarn,
- TmpMods};
- {ok, NewCG, NoWarn, NewCServer, Mod} ->
- {NewCG, NewCServer, TmpFailed, NoWarn++TmpNoWarn,
- [Mod|TmpMods]}
- end
- end;
- byte_code ->
- fun(File, {TmpCG, TmpCServer, TmpFailed, TmpNoWarn, TmpMods}) ->
- case compile_byte(File, TmpCG, TmpCServer, UseContracts) of
- {error, Reason} ->
- {TmpCG, TmpCServer, [{File, Reason}|TmpFailed], TmpNoWarn,
- TmpMods};
- {ok, NewCG, NoWarn, NewCServer, Mod} ->
- {NewCG, NewCServer, TmpFailed, NoWarn++TmpNoWarn,
- [Mod|TmpMods]}
- end
- end
- end,
- {NewCallgraph1, NewCServer, Failed, NoWarn, Modules} =
- lists:foldl(Fun, {Callgraph, CServer, [], [], []}, Files),
+ CompileInit = make_compile_init(State, Callgraph),
+ {{Failed, NoWarn, Modules}, NextLabel} =
+ ?timing(Timing, "compile", _C1,
+ dialyzer_coordinator:parallel_job(compile, Files,
+ CompileInit, Timing)),
+ CServer2 = dialyzer_codeserver:set_next_core_label(NextLabel, CServer),
case Failed =:= [] of
true ->
NewFiles = lists:zip(lists:reverse(Modules), Files),
@@ -255,11 +264,56 @@ compile_and_store(Files, #analysis_state{codeserver = CServer,
{T2, _} = statistics(runtime),
Msg1 = io_lib:format("done in ~.2f secs\nRemoving edges... ", [(T2-T1)/1000]),
send_log(Parent, Msg1),
- NewCallgraph2 = cleanup_callgraph(State, NewCServer, NewCallgraph1, Modules),
+ Callgraph =
+ ?timing(Timing, "clean", _C2,
+ cleanup_callgraph(State, CServer2, Callgraph, Modules)),
{T3, _} = statistics(runtime),
Msg2 = io_lib:format("done in ~.2f secs\n", [(T3-T2)/1000]),
send_log(Parent, Msg2),
- {NewCallgraph2, sets:from_list(NoWarn), NewCServer}.
+ {Callgraph, sets:from_list(NoWarn), CServer2}.
+
+-type compile_init_data() :: #compile_init{}.
+-type error_reason() :: string().
+-type compile_result() :: {[{file:filename(), error_reason()}], [mfa()],
+ [module()]}. %%opaque
+-type one_file_result() :: {error, error_reason()} |
+ {ok, [dialyzer_callgraph:callgraph_edge()],
+ [mfa_or_funlbl()], [mfa()], module()}. %%opaque
+-type compile_mid_data() :: {module(), cerl:cerl(), [mfa()],
+ dialyzer_callgraph:callgraph(),
+ dialyzer_codeserver:codeserver()}.
+
+-spec compile_init_result() -> compile_result().
+
+compile_init_result() -> {[], [], []}.
+
+-spec add_to_result(file:filename(), one_file_result(), compile_result(),
+ compile_init_data()) -> compile_result().
+
+add_to_result(File, NewData, {Failed, NoWarn, Mods}, InitData) ->
+ case NewData of
+ {error, Reason} ->
+ {[{File, Reason}|Failed], NoWarn, Mods};
+ {ok, V, E, NewNoWarn, Mod} ->
+ Callgraph = InitData#compile_init.callgraph,
+ dialyzer_callgraph:add_edges(E, V, Callgraph),
+ {Failed, NewNoWarn ++ NoWarn, [Mod|Mods]}
+ end.
+
+-spec start_compilation(file:filename(), compile_init_data()) ->
+ {error, error_reason()} |{ok, integer(), compile_mid_data()}.
+
+start_compilation(File,
+ #compile_init{callgraph = Callgraph, codeserver = Codeserver,
+ defines = Defines, include_dirs = IncludeD,
+ use_contracts = UseContracts,
+ start_from = StartFrom}) ->
+ case StartFrom of
+ src_code ->
+ compile_src(File, IncludeD, Defines, Callgraph, Codeserver, UseContracts);
+ byte_code ->
+ compile_byte(File, Callgraph, Codeserver, UseContracts)
+ end.
cleanup_callgraph(#analysis_state{plt = InitPlt, parent = Parent,
codeserver = CodeServer
@@ -348,14 +402,18 @@ compile_common(File, AbstrCode, CompOpts, Callgraph, CServer, UseContracts) ->
store_core(Mod, Core, NoWarn, Callgraph, CServer) ->
Exp = get_exports_from_core(Core),
- OldExpTypes = dialyzer_codeserver:get_temp_exported_types(CServer),
- NewExpTypes = get_exported_types_from_core(Core),
- MergedExpTypes = sets:union(NewExpTypes, OldExpTypes),
- CServer1 = dialyzer_codeserver:insert_exports(Exp, CServer),
- CServer2 = dialyzer_codeserver:insert_temp_exported_types(MergedExpTypes,
- CServer1),
- {LabeledCore, CServer3} = label_core(Core, CServer2),
- store_code_and_build_callgraph(Mod, LabeledCore, Callgraph, CServer3, NoWarn).
+ ExpTypes = get_exported_types_from_core(Core),
+ CServer = dialyzer_codeserver:insert_exports(Exp, CServer),
+ CServer = dialyzer_codeserver:insert_temp_exported_types(ExpTypes, CServer),
+ CoreTree = cerl:from_records(Core),
+ {ok, cerl_trees:size(CoreTree), {Mod, CoreTree, NoWarn, Callgraph, CServer}}.
+
+-spec continue_compilation(integer(), compile_mid_data()) -> one_file_result().
+
+continue_compilation(NextLabel, {Mod, CoreTree, NoWarn, Callgraph, CServer}) ->
+ {LabeledTree, _NewNextLabel} = cerl_trees:label(CoreTree, NextLabel),
+ LabeledCore = cerl:to_records(LabeledTree),
+ store_code_and_build_callgraph(Mod, LabeledCore, Callgraph, NoWarn, CServer).
abs_get_nowarn(Abs, M) ->
Opts = lists:flatten([C || {attribute, _, compile, C} <- Abs]),
@@ -388,18 +446,11 @@ get_exports_from_core(Core) ->
M = cerl:atom_val(cerl:module_name(Tree)),
[{M, F, A} || {F, A} <- Exports2].
-label_core(Core, CServer) ->
- NextLabel = dialyzer_codeserver:get_next_core_label(CServer),
- CoreTree = cerl:from_records(Core),
- {LabeledTree, NewNextLabel} = cerl_trees:label(CoreTree, NextLabel),
- {cerl:to_records(LabeledTree),
- dialyzer_codeserver:set_next_core_label(NewNextLabel, CServer)}.
-
-store_code_and_build_callgraph(Mod, Core, Callgraph, CServer, NoWarn) ->
+store_code_and_build_callgraph(Mod, Core, Callgraph, NoWarn, CServer) ->
CoreTree = cerl:from_records(Core),
- NewCallgraph = dialyzer_callgraph:scan_core_tree(CoreTree, Callgraph),
- CServer2 = dialyzer_codeserver:insert(Mod, CoreTree, CServer),
- {ok, NewCallgraph, NoWarn, CServer2, Mod}.
+ {Vertices, Edges} = dialyzer_callgraph:scan_core_tree(CoreTree, Callgraph),
+ CServer = dialyzer_codeserver:insert(Mod, CoreTree, CServer),
+ {ok, Vertices, Edges, NoWarn, Mod}.
%%--------------------------------------------------------------------
%% Utilities
diff --git a/lib/dialyzer/src/dialyzer_behaviours.erl b/lib/dialyzer/src/dialyzer_behaviours.erl
index 127e906135..b84071b95c 100644
--- a/lib/dialyzer/src/dialyzer_behaviours.erl
+++ b/lib/dialyzer/src/dialyzer_behaviours.erl
@@ -30,7 +30,7 @@
-module(dialyzer_behaviours).
--export([check_callbacks/4, get_behaviour_apis/1,
+-export([check_callbacks/5, get_behaviour_apis/1,
translate_behaviour_api_call/5, translatable_behaviours/1,
translate_callgraph/3]).
@@ -47,15 +47,16 @@
-record(state, {plt :: dialyzer_plt:plt(),
codeserver :: dialyzer_codeserver:codeserver(),
filename :: file:filename(),
- behlines :: [{behaviour(), non_neg_integer()}]}).
+ behlines :: [{behaviour(), non_neg_integer()}],
+ records :: dict()}).
%%--------------------------------------------------------------------
--spec check_callbacks(module(), [{cerl:cerl(), cerl:cerl()}],
+-spec check_callbacks(module(), [{cerl:cerl(), cerl:cerl()}], dict(),
dialyzer_plt:plt(),
dialyzer_codeserver:codeserver()) -> [dial_warning()].
-check_callbacks(Module, Attrs, Plt, Codeserver) ->
+check_callbacks(Module, Attrs, Records, Plt, Codeserver) ->
{Behaviours, BehLines} = get_behaviours(Attrs),
case Behaviours of
[] -> [];
@@ -64,7 +65,7 @@ check_callbacks(Module, Attrs, Plt, Codeserver) ->
{_Var,Code} = dialyzer_codeserver:lookup_mfa_code(MFA, Codeserver),
File = get_file(cerl:get_ann(Code)),
State = #state{plt = Plt, filename = File, behlines = BehLines,
- codeserver = Codeserver},
+ codeserver = Codeserver, records = Records},
Warnings = get_warnings(Module, Behaviours, State),
[add_tag_file_line(Module, W, State) || W <- Warnings]
end.
@@ -92,24 +93,21 @@ get_warnings(Module, [Behaviour|Rest], State, Acc) ->
check_behaviour(Module, Behaviour, #state{plt = Plt} = State, Acc) ->
case dialyzer_plt:lookup_callbacks(Plt, Behaviour) of
- [] -> [{callback_info_missing, [Behaviour]}|Acc];
- Callbacks -> check_all_callbacks(Module, Behaviour, Callbacks, State, Acc)
+ none -> [{callback_info_missing, [Behaviour]}|Acc];
+ {value, Callbacks} ->
+ check_all_callbacks(Module, Behaviour, Callbacks, State, Acc)
end.
check_all_callbacks(_Module, _Behaviour, [], _State, Acc) ->
Acc;
check_all_callbacks(Module, Behaviour, [Cb|Rest],
- #state{plt = Plt, codeserver = Codeserver} = State, Acc) ->
+ #state{plt = Plt, codeserver = Codeserver,
+ records = Records} = State, Acc) ->
{{Behaviour, Function, Arity},
{{_BehFile, _BehLine}, Callback}} = Cb,
CbMFA = {Module, Function, Arity},
CbReturnType = dialyzer_contracts:get_contract_return(Callback),
CbArgTypes = dialyzer_contracts:get_contract_args(Callback),
- Records =
- case dict:find(Module, dialyzer_codeserver:get_records(Codeserver)) of
- {ok, V} -> V;
- error -> dict:new()
- end,
Acc0 = Acc,
Acc1 =
case dialyzer_plt:lookup(Plt, CbMFA) of
@@ -282,8 +280,8 @@ translate_callgraph([{Behaviour,_}|Behaviours], Module, Callgraph) ->
DirectCalls = [{From, {Module, Fun, Arity}} ||
{From, To} <- UsedCalls,{API, {Fun, Arity, _Ord}} <- Calls,
To =:= API],
- NewCallgraph = dialyzer_callgraph:add_edges(DirectCalls, Callgraph),
- translate_callgraph(Behaviours, Module, NewCallgraph);
+ dialyzer_callgraph:add_edges(DirectCalls, Callgraph),
+ translate_callgraph(Behaviours, Module, Callgraph);
translate_callgraph([], _Module, Callgraph) ->
Callgraph.
diff --git a/lib/dialyzer/src/dialyzer_callgraph.erl b/lib/dialyzer/src/dialyzer_callgraph.erl
index effd619bde..64e0ee88af 100644
--- a/lib/dialyzer/src/dialyzer_callgraph.erl
+++ b/lib/dialyzer/src/dialyzer_callgraph.erl
@@ -28,6 +28,7 @@
-module(dialyzer_callgraph).
-export([add_edges/2,
+ add_edges/3,
all_nodes/1,
delete/1,
finalize/1,
@@ -43,12 +44,15 @@
%% module_postorder/1,
module_postorder_from_funs/2,
new/0,
+ get_depends_on/2,
+ get_required_by/2,
in_neighbours/2,
renew_race_info/4,
+ renew_race_code/2,
+ renew_race_public_tables/2,
reset_from_funs/2,
scan_core_tree/2,
strip_module_deps/2,
- take_scc/1,
remove_external/1,
to_dot/2,
to_ps/3]).
@@ -57,15 +61,14 @@
get_race_code/1, get_race_detection/1, race_code_new/1,
put_digraph/2, put_race_code/2, put_race_detection/2,
put_named_tables/2, put_public_tables/2, put_behaviour_api_calls/2,
- get_behaviour_api_calls/1]).
+ get_behaviour_api_calls/1, dispose_race_server/1, duplicate/1]).
--export_type([callgraph/0, mfa_or_funlbl/0]).
+-export_type([callgraph/0, mfa_or_funlbl/0, callgraph_edge/0]).
-include("dialyzer.hrl").
%%----------------------------------------------------------------------
--type mfa_or_funlbl() :: label() | mfa().
-type scc() :: [mfa_or_funlbl()].
-type mfa_calls() :: [{mfa_or_funlbl(), mfa_or_funlbl()}].
@@ -78,9 +81,6 @@
%% digraph - A digraph representing the callgraph.
%% Nodes are represented as MFAs or labels.
%% esc - A set of all escaping functions as reported by dialyzer_dep.
-%% postorder - A list of strongly connected components of the callgraph
-%% sorted in a topological bottom-up order.
-%% This is produced by calling finalize/1.
%% name_map - A mapping from label to MFA.
%% rev_name_map - A reverse mapping of the name_map.
%% rec_var_map - A dict mapping from letrec bound labels to function names.
@@ -91,29 +91,42 @@
%%-----------------------------------------------------------------------------
-record(callgraph, {digraph = digraph:new() :: digraph(),
- esc = sets:new() :: set(),
- name_map = dict:new() :: dict(),
- rev_name_map = dict:new() :: dict(),
- postorder = [] :: [scc()],
- rec_var_map = dict:new() :: dict(),
- self_rec = sets:new() :: set(),
- calls = dict:new() :: dict(),
- race_code = dict:new() :: dict(),
- public_tables = [] :: [label()],
- named_tables = [] :: [string()],
+ active_digraph :: active_digraph(),
+ esc :: ets:tid(),
+ name_map :: ets:tid(),
+ rev_name_map :: ets:tid(),
+ rec_var_map :: ets:tid(),
+ self_rec :: ets:tid(),
+ calls :: ets:tid(),
race_detection = false :: boolean(),
- beh_api_calls = [] :: [{mfa(), mfa()}]}).
+ race_data_server = new_race_data_server() :: pid()}).
+
+-record(race_data_state, {race_code = dict:new() :: dict(),
+ public_tables = [] :: [label()],
+ named_tables = [] :: [string()],
+ beh_api_calls = [] :: [{mfa(), mfa()}]}).
%% Exported Types
-type callgraph() :: #callgraph{}.
+-type active_digraph() :: {'d', digraph()} | {'e', ets:tid(), ets:tid()}.
+
%%----------------------------------------------------------------------
-spec new() -> callgraph().
new() ->
- #callgraph{}.
+ [ETSEsc, ETSNameMap, ETSRevNameMap, ETSRecVarMap, ETSSelfRec, ETSCalls] =
+ [ets:new(N,[public, {read_concurrency, true}]) ||
+ N <- [callgraph_esc, callgraph_name_map, callgraph_rev_name_map,
+ callgraph_rec_var_map, callgraph_self_rec, callgraph_calls]],
+ #callgraph{esc = ETSEsc,
+ name_map = ETSNameMap,
+ rev_name_map = ETSRevNameMap,
+ rec_var_map = ETSRecVarMap,
+ self_rec = ETSSelfRec,
+ calls = ETSCalls}.
-spec delete(callgraph()) -> 'true'.
@@ -129,32 +142,32 @@ all_nodes(#callgraph{digraph = DG}) ->
lookup_rec_var(Label, #callgraph{rec_var_map = RecVarMap})
when is_integer(Label) ->
- dict:find(Label, RecVarMap).
+ ets_lookup_dict(Label, RecVarMap).
-spec lookup_call_site(label(), callgraph()) -> 'error' | {'ok', [_]}. % XXX: refine
lookup_call_site(Label, #callgraph{calls = Calls})
when is_integer(Label) ->
- dict:find(Label, Calls).
+ ets_lookup_dict(Label, Calls).
-spec lookup_name(label(), callgraph()) -> 'error' | {'ok', mfa()}.
lookup_name(Label, #callgraph{name_map = NameMap})
when is_integer(Label) ->
- dict:find(Label, NameMap).
+ ets_lookup_dict(Label, NameMap).
-spec lookup_label(mfa_or_funlbl(), callgraph()) -> 'error' | {'ok', integer()}.
lookup_label({_,_,_} = MFA, #callgraph{rev_name_map = RevNameMap}) ->
- dict:find(MFA, RevNameMap);
+ ets_lookup_dict(MFA, RevNameMap);
lookup_label(Label, #callgraph{}) when is_integer(Label) ->
{ok, Label}.
-spec in_neighbours(mfa_or_funlbl(), callgraph()) -> 'none' | [mfa_or_funlbl(),...].
-in_neighbours(Label, #callgraph{digraph = Digraph, name_map = NameMap})
+in_neighbours(Label, #callgraph{digraph = Digraph} = CG)
when is_integer(Label) ->
- Name = case dict:find(Label, NameMap) of
+ Name = case lookup_name(Label, CG) of
{ok, Val} -> Val;
error -> Label
end,
@@ -165,34 +178,27 @@ in_neighbours({_, _, _} = MFA, #callgraph{digraph = Digraph}) ->
-spec is_self_rec(mfa_or_funlbl(), callgraph()) -> boolean().
is_self_rec(MfaOrLabel, #callgraph{self_rec = SelfRecs}) ->
- sets:is_element(MfaOrLabel, SelfRecs).
+ ets_lookup_set(MfaOrLabel, SelfRecs).
-spec is_escaping(label(), callgraph()) -> boolean().
is_escaping(Label, #callgraph{esc = Esc}) when is_integer(Label) ->
- sets:is_element(Label, Esc).
+ ets_lookup_set(Label, Esc).
-type callgraph_edge() :: {mfa_or_funlbl(),mfa_or_funlbl()}.
--spec add_edges([callgraph_edge()], callgraph()) -> callgraph().
+-spec add_edges([callgraph_edge()], callgraph()) -> ok.
-add_edges([], CG) ->
- CG;
-add_edges(Edges, #callgraph{digraph = Digraph} = CG) ->
- CG#callgraph{digraph = digraph_add_edges(Edges, Digraph)}.
+add_edges([], _CG) ->
+ ok;
+add_edges(Edges, #callgraph{digraph = Digraph}) ->
+ digraph_add_edges(Edges, Digraph).
--spec add_edges([callgraph_edge()], [mfa_or_funlbl()], callgraph()) -> callgraph().
+-spec add_edges([callgraph_edge()], [mfa_or_funlbl()], callgraph()) -> ok.
add_edges(Edges, MFAs, #callgraph{digraph = DG} = CG) ->
- DG = digraph_confirm_vertices(MFAs, DG),
+ digraph_confirm_vertices(MFAs, DG),
add_edges(Edges, CG).
--spec take_scc(callgraph()) -> 'none' | {'ok', scc(), callgraph()}.
-
-take_scc(#callgraph{postorder = [SCC|SCCs]} = CG) ->
- {ok, SCC, CG#callgraph{postorder = SCCs}};
-take_scc(#callgraph{postorder = []}) ->
- none.
-
-spec remove_external(callgraph()) -> {callgraph(), [tuple()]}.
remove_external(#callgraph{digraph = DG} = CG) ->
@@ -221,13 +227,25 @@ find_non_local_calls([{Label1, Label2}|Left], Set) when is_integer(Label1),
find_non_local_calls([], Set) ->
sets:to_list(Set).
--spec renew_race_info(callgraph(), dict(), [label()], [string()]) ->
- callgraph().
+-spec get_depends_on(scc() | module(), callgraph()) -> [scc()].
+
+get_depends_on(SCC, #callgraph{active_digraph = {'e', Out, _In}}) ->
+ case ets_lookup_dict(SCC, Out) of
+ {ok, Value} -> Value;
+ error -> []
+ end;
+get_depends_on(SCC, #callgraph{active_digraph = {'d', DG}}) ->
+ digraph:out_neighbours(DG, SCC).
+
+-spec get_required_by(scc() | module(), callgraph()) -> [scc()].
-renew_race_info(CG, RaceCode, PublicTables, NamedTables) ->
- CG#callgraph{race_code = RaceCode,
- public_tables = PublicTables,
- named_tables = NamedTables}.
+get_required_by(SCC, #callgraph{active_digraph = {'e', _Out, In}}) ->
+ case ets_lookup_dict(SCC, In) of
+ {ok, Value} -> Value;
+ error -> []
+ end;
+get_required_by(SCC, #callgraph{active_digraph = {'d', DG}}) ->
+ digraph:in_neighbours(DG, SCC).
%%----------------------------------------------------------------------
%% Handling of modules & SCCs
@@ -238,32 +256,37 @@ renew_race_info(CG, RaceCode, PublicTables, NamedTables) ->
modules(#callgraph{digraph = DG}) ->
ordsets:from_list([M || {M,_F,_A} <- digraph_vertices(DG)]).
--spec module_postorder(callgraph()) -> [[module()]].
+-spec module_postorder(callgraph()) -> {[module()], {'d', digraph()}}.
module_postorder(#callgraph{digraph = DG}) ->
- {MDG, _Nodes} = get_module_digraph_and_nodes(DG),
- MDG1 = digraph_utils:condensation(MDG),
- PostOrder = digraph_utils:postorder(MDG1),
- PostOrder1 = sort_sccs_internally(PostOrder, MDG),
- digraph:delete(MDG1),
- digraph_delete(MDG),
- PostOrder1.
+ Edges = lists:foldl(fun edge_fold/2, sets:new(), digraph_edges(DG)),
+ Nodes = sets:from_list([M || {M,_F,_A} <- digraph_vertices(DG)]),
+ MDG = digraph:new([acyclic]),
+ digraph_confirm_vertices(sets:to_list(Nodes), MDG),
+ Foreach = fun({M1,M2}) -> digraph:add_edge(MDG, M1, M2) end,
+ lists:foreach(Foreach, sets:to_list(Edges)),
+ {digraph_utils:topsort(MDG), {'d', MDG}}.
+
+edge_fold({{M1,_,_},{M2,_,_}}, Set) ->
+ case M1 =/= M2 of
+ true -> sets:add_element({M1,M2},Set);
+ false -> Set
+ end;
+edge_fold(_, Set) -> Set.
-get_module_digraph_and_nodes(DG) ->
- Edges = digraph_edges(DG),
- Nodes = ordsets:from_list([M || {M,_F,_A} <- digraph_vertices(DG)]),
- MDG = digraph:new(),
- MDG = digraph_confirm_vertices(Nodes, MDG),
- MDG = create_module_digraph(Edges, MDG),
- {MDG, Nodes}.
%% The module deps of a module are modules that depend on the module
-spec module_deps(callgraph()) -> dict().
module_deps(#callgraph{digraph = DG}) ->
- {MDG, Nodes} = get_module_digraph_and_nodes(DG),
+ Edges = lists:foldl(fun edge_fold/2, sets:new(), digraph_edges(DG)),
+ Nodes = sets:from_list([M || {M,_F,_A} <- digraph_vertices(DG)]),
+ MDG = digraph:new(),
+ digraph_confirm_vertices(sets:to_list(Nodes), MDG),
+ Foreach = fun({M1,M2}) -> digraph:add_edge(MDG, M1, M2) end,
+ lists:foreach(Foreach, sets:to_list(Edges)),
Deps = [{N, ordsets:from_list(digraph:in_neighbours(MDG, N))}
- || N <- Nodes],
+ || N <- sets:to_list(Nodes)],
digraph_delete(MDG),
dict:from_list(Deps).
@@ -276,52 +299,42 @@ strip_module_deps(ModDeps, StripSet) ->
FilterFun2 = fun(_Key, ValSet) -> ValSet =/= [] end,
dict:filter(FilterFun2, ModDeps1).
-sort_sccs_internally(PO, MDG) ->
- sort_sccs_internally(PO, MDG, []).
-
-sort_sccs_internally([SCC|SCCs], MDG, Acc) ->
- case SCC of
- [_, _, _ | _] -> % length(SCC) >= 3
- TmpDG = digraph_utils:subgraph(MDG, SCC),
- NewSCC = digraph_utils:postorder(TmpDG),
- digraph_delete(TmpDG),
- sort_sccs_internally(SCCs, MDG, [NewSCC|Acc]);
- _ ->
- sort_sccs_internally(SCCs, MDG, [SCC|Acc])
- end;
-sort_sccs_internally([], _MDG, Acc) ->
- lists:reverse(Acc).
-
-create_module_digraph([{{M, _, _}, {M, _, _}}|Left], MDG) ->
- create_module_digraph(Left, MDG);
-create_module_digraph([{{M1, _, _}, {M2, _, _}}|Left], MDG) ->
- create_module_digraph(Left, digraph_add_edge(M1, M2, MDG));
-create_module_digraph([{_, _}|Left], MDG) ->
- create_module_digraph(Left, MDG);
-create_module_digraph([], MDG) ->
- MDG.
-
--spec finalize(callgraph()) -> callgraph().
+-spec finalize(callgraph()) -> {[scc()], callgraph()}.
finalize(#callgraph{digraph = DG} = CG) ->
- CG#callgraph{postorder = digraph_finalize(DG)}.
+ {ActiveDG, Postorder} = condensation(DG),
+ {Postorder, CG#callgraph{active_digraph = ActiveDG}}.
--spec reset_from_funs([mfa_or_funlbl()], callgraph()) -> callgraph().
+-spec reset_from_funs([mfa_or_funlbl()], callgraph()) -> {[scc()], callgraph()}.
-reset_from_funs(Funs, #callgraph{digraph = DG} = CG) ->
+reset_from_funs(Funs, #callgraph{digraph = DG, active_digraph = ADG} = CG) ->
+ active_digraph_delete(ADG),
SubGraph = digraph_reaching_subgraph(Funs, DG),
- Postorder = digraph_finalize(SubGraph),
+ {NewActiveDG, Postorder} = condensation(SubGraph),
digraph_delete(SubGraph),
- CG#callgraph{postorder = Postorder}.
+ {Postorder, CG#callgraph{active_digraph = NewActiveDG}}.
--spec module_postorder_from_funs([mfa_or_funlbl()], callgraph()) -> [[module()]].
+-spec module_postorder_from_funs([mfa_or_funlbl()], callgraph()) ->
+ {[module()], callgraph()}.
-module_postorder_from_funs(Funs, #callgraph{digraph = DG} = CG) ->
+module_postorder_from_funs(Funs, #callgraph{digraph = DG,
+ active_digraph = ADG} = CG) ->
+ active_digraph_delete(ADG),
SubGraph = digraph_reaching_subgraph(Funs, DG),
- PO = module_postorder(CG#callgraph{digraph = SubGraph}),
+ {PO, Active} = module_postorder(CG#callgraph{digraph = SubGraph}),
digraph_delete(SubGraph),
- PO.
-
+ {PO, CG#callgraph{active_digraph = Active}}.
+
+ets_lookup_dict(Key, Table) ->
+ try ets:lookup_element(Table, Key, 2) of
+ Val -> {ok, Val}
+ catch
+ _:_ -> error
+ end.
+
+ets_lookup_set(Key, Table) ->
+ ets:lookup(Table, Key) =/= [].
+
%%----------------------------------------------------------------------
%% Core code
%%----------------------------------------------------------------------
@@ -330,36 +343,37 @@ module_postorder_from_funs(Funs, #callgraph{digraph = DG} = CG) ->
%% The set of labels in the tree must be disjoint from the set of
%% labels already occuring in the callgraph.
--spec scan_core_tree(cerl:c_module(), callgraph()) -> callgraph().
+-spec scan_core_tree(cerl:c_module(), callgraph()) ->
+ {[mfa_or_funlbl()], [callgraph_edge()]}.
-scan_core_tree(Tree, #callgraph{calls = OldCalls,
- esc = OldEsc,
- name_map = OldNameMap,
- rec_var_map = OldRecVarMap,
- rev_name_map = OldRevNameMap,
- self_rec = OldSelfRec} = CG) ->
+scan_core_tree(Tree, #callgraph{calls = ETSCalls,
+ esc = ETSEsc,
+ name_map = ETSNameMap,
+ rec_var_map = ETSRecVarMap,
+ rev_name_map = ETSRevNameMap,
+ self_rec = ETSSelfRec}) ->
%% Build name map and recursion variable maps.
- {NewNameMap, NewRevNameMap, NewRecVarMap} =
- build_maps(Tree, OldRecVarMap, OldNameMap, OldRevNameMap),
-
+ build_maps(Tree, ETSRecVarMap, ETSNameMap, ETSRevNameMap),
+
%% First find the module-local dependencies.
{Deps0, EscapingFuns, Calls} = dialyzer_dep:analyze(Tree),
- NewCalls = dict:merge(fun(_Key, Val, Val) -> Val end, OldCalls, Calls),
- NewEsc = sets:union(sets:from_list(EscapingFuns), OldEsc),
+ true = ets:insert(ETSCalls, dict:to_list(Calls)),
+ true = ets:insert(ETSEsc, [{E} || E <- EscapingFuns]),
+
LabelEdges = get_edges_from_deps(Deps0),
%% Find the self recursive functions. Named functions get both the
%% key and their name for convenience.
SelfRecs0 = lists:foldl(fun({Key, Key}, Acc) ->
- case dict:find(Key, NewNameMap) of
+ case ets_lookup_dict(Key, ETSNameMap) of
error -> [Key|Acc];
{ok, Name} -> [Key, Name|Acc]
end;
(_, Acc) -> Acc
end, [], LabelEdges),
- SelfRecs = sets:union(sets:from_list(SelfRecs0), OldSelfRec),
+ true = ets:insert(ETSSelfRec, [{S} || S <- SelfRecs0]),
- NamedEdges1 = name_edges(LabelEdges, NewNameMap),
+ NamedEdges1 = name_edges(LabelEdges, ETSNameMap),
%% We need to scan for inter-module calls since these are not tracked
%% by dialyzer_dep. Note that the caller is always recorded as the
@@ -378,27 +392,25 @@ scan_core_tree(Tree, #callgraph{calls = OldCalls,
NewNamedEdges1 =
[E || {From, To} = E <- NamedEdges1, From =/= top, To =/= top],
NamedEdges3 = NewNamedEdges1 ++ NewNamedEdges2,
- CG1 = add_edges(NamedEdges3, Names3, CG),
- CG1#callgraph{calls = NewCalls,
- esc = NewEsc,
- name_map = NewNameMap,
- rec_var_map = NewRecVarMap,
- rev_name_map = NewRevNameMap,
- self_rec = SelfRecs}.
-
-build_maps(Tree, RecVarMap, NameMap, RevNameMap) ->
+ {Names3, NamedEdges3}.
+
+build_maps(Tree, ETSRecVarMap, ETSNameMap, ETSRevNameMap) ->
%% We only care about the named (top level) functions. The anonymous
%% functions will be analysed together with their parents.
Defs = cerl:module_defs(Tree),
Mod = cerl:atom_val(cerl:module_name(Tree)),
- lists:foldl(fun({Var, Function}, {AccNameMap, AccRevNameMap, AccRecVarMap}) ->
- FunName = cerl:fname_id(Var),
- Arity = cerl:fname_arity(Var),
- MFA = {Mod, FunName, Arity},
- {dict:store(get_label(Function), MFA, AccNameMap),
- dict:store(MFA, get_label(Function), AccRevNameMap),
- dict:store(get_label(Var), MFA, AccRecVarMap)}
- end, {NameMap, RevNameMap, RecVarMap}, Defs).
+ Fun =
+ fun({Var, Function}) ->
+ FunName = cerl:fname_id(Var),
+ Arity = cerl:fname_arity(Var),
+ MFA = {Mod, FunName, Arity},
+ FunLabel = get_label(Function),
+ VarLabel = get_label(Var),
+ true = ets:insert(ETSNameMap, {FunLabel, MFA}),
+ true = ets:insert(ETSRevNameMap, {MFA, FunLabel}),
+ true = ets:insert(ETSRecVarMap, {VarLabel, MFA})
+ end,
+ lists:foreach(Fun, Defs).
get_edges_from_deps(Deps) ->
%% Convert the dependencies as produced by dialyzer_dep to a list of
@@ -411,22 +423,22 @@ get_edges_from_deps(Deps) ->
end, [], Deps),
lists:flatten(Edges).
-name_edges(Edges, NameMap) ->
+name_edges(Edges, ETSNameMap) ->
%% If a label is present in the name map it is renamed. Otherwise
%% keep the label as the identity.
MapFun = fun(X) ->
- case dict:find(X, NameMap) of
+ case ets_lookup_dict(X, ETSNameMap) of
error -> X;
{ok, MFA} -> MFA
end
end,
- name_edges(Edges, MapFun, NameMap, []).
+ name_edges(Edges, MapFun, []).
-name_edges([{From, To}|Left], MapFun, NameMap, Acc) ->
+name_edges([{From, To}|Left], MapFun, Acc) ->
NewFrom = MapFun(From),
NewTo = MapFun(To),
- name_edges(Left, MapFun, NameMap, [{NewFrom, NewTo}|Acc]);
-name_edges([], _MapFun, _NameMap, Acc) ->
+ name_edges(Left, MapFun, [{NewFrom, NewTo}|Acc]);
+name_edges([], _MapFun, Acc) ->
Acc.
scan_core_funs(Tree) ->
@@ -478,9 +490,10 @@ get_label(T) ->
%%----------------------------------------------------------------------
digraph_add_edges([{From, To}|Left], DG) ->
- digraph_add_edges(Left, digraph_add_edge(From, To, DG));
-digraph_add_edges([], DG) ->
- DG.
+ digraph_add_edge(From, To, DG),
+ digraph_add_edges(Left, DG);
+digraph_add_edges([], _DG) ->
+ ok.
digraph_add_edge(From, To, DG) ->
case digraph:vertex(DG, From) of
@@ -492,13 +505,13 @@ digraph_add_edge(From, To, DG) ->
{To, _} -> ok
end,
digraph:add_edge(DG, {From, To}, From, To, []),
- DG.
+ ok.
digraph_confirm_vertices([MFA|Left], DG) ->
digraph:add_vertex(DG, MFA, confirmed),
digraph_confirm_vertices(Left, DG);
-digraph_confirm_vertices([], DG) ->
- DG.
+digraph_confirm_vertices([], _DG) ->
+ ok.
digraph_remove_external(DG) ->
Vertices = digraph:vertices(DG),
@@ -522,6 +535,12 @@ remove_unconfirmed([], DG, Unconfirmed) ->
digraph_delete(DG) ->
digraph:delete(DG).
+active_digraph_delete({'d', DG}) ->
+ digraph:delete(DG);
+active_digraph_delete({'e', Out, In}) ->
+ ets:delete(Out),
+ ets:delete(In).
+
digraph_edges(DG) ->
digraph:edges(DG).
@@ -534,75 +553,6 @@ digraph_in_neighbours(V, DG) ->
List -> List
end.
-%% Pick all the independent nodes (leaves) from one module. Then try
-%% to stay within the module until no more independent nodes can be
-%% chosen. Then pick a new module and so on.
-%%
-%% Note that an SCC that ranges over more than one module is
-%% considered to belong to all modules to make sure that we do not
-%% lose any nodes.
-
-digraph_postorder(Digraph) ->
- %% Remove all self-edges for SCCs.
- Edges = [digraph:edge(Digraph, E) || E <- digraph:edges(Digraph)],
- SelfEdges = [E || {E, V, V, _} <- Edges],
- true = digraph:del_edges(Digraph, SelfEdges),
- %% Determine the first module outside of the loop.
- Leaves = digraph_leaves(Digraph),
- case Leaves =:= [] of
- true -> [];
- false ->
- {Module, Taken} = take_sccs_from_fresh_module(Leaves),
- true = digraph:del_vertices(Digraph, Taken),
- digraph_postorder(Digraph, Module, [Taken])
- end.
-
-digraph_postorder(Digraph, LastModule, Acc) ->
- Leaves = digraph_leaves(Digraph),
- case Leaves =:= [] of
- true -> lists:append(lists:reverse(Acc));
- false ->
- case [SCC || SCC <- Leaves, scc_belongs_to_module(SCC, LastModule)] of
- [] ->
- {NewModule, NewTaken} = take_sccs_from_fresh_module(Leaves),
- true = digraph:del_vertices(Digraph, NewTaken),
- digraph_postorder(Digraph, NewModule, [NewTaken|Acc]);
- NewTaken ->
- true = digraph:del_vertices(Digraph, NewTaken),
- digraph_postorder(Digraph, LastModule, [NewTaken|Acc])
- end
- end.
-
-digraph_leaves(Digraph) ->
- [V || V <- digraph:vertices(Digraph), digraph:out_degree(Digraph, V) =:= 0].
-
-take_sccs_from_fresh_module(Leaves) ->
- NewModule = find_module(hd(Leaves)),
- {NewModule,
- [SCC || SCC <- Leaves, scc_belongs_to_module(SCC, NewModule)]}.
-
--spec scc_belongs_to_module(scc(), module()) -> boolean().
-
-scc_belongs_to_module([Label|Left], Module) when is_integer(Label) ->
- scc_belongs_to_module(Left, Module);
-scc_belongs_to_module([{M, _, _}|Left], Module) ->
- if M =:= Module -> true;
- true -> scc_belongs_to_module(Left, Module)
- end;
-scc_belongs_to_module([], _Module) ->
- false.
-
--spec find_module(scc()) -> module().
-
-find_module([{M, _, _}|_]) -> M;
-find_module([Label|Left]) when is_integer(Label) -> find_module(Left).
-
-digraph_finalize(DG) ->
- DG1 = digraph_utils:condensation(DG),
- Postorder = digraph_postorder(DG1),
- digraph:delete(DG1),
- Postorder.
-
digraph_reaching_subgraph(Funs, DG) ->
Vertices = digraph_utils:reaching(Funs, DG),
digraph_utils:subgraph(DG, Vertices).
@@ -611,20 +561,71 @@ digraph_reaching_subgraph(Funs, DG) ->
%% Races
%%----------------------------------------------------------------------
+-spec renew_race_info(callgraph(), dict(), [label()], [string()]) ->
+ callgraph().
+
+renew_race_info(#callgraph{race_data_server = RaceDataServer} = CG,
+ RaceCode, PublicTables, NamedTables) ->
+ ok = race_data_server_cast(
+ {renew_race_info, {RaceCode, PublicTables, NamedTables}},
+ RaceDataServer),
+ CG.
+
+renew_race_info({RaceCode, PublicTables, NamedTables},
+ #race_data_state{} = State) ->
+ State#race_data_state{race_code = RaceCode,
+ public_tables = PublicTables,
+ named_tables = NamedTables}.
+
+-spec renew_race_code(dialyzer_races:races(), callgraph()) -> callgraph().
+
+renew_race_code(Races, #callgraph{race_data_server = RaceDataServer} = CG) ->
+ Fun = dialyzer_races:get_curr_fun(Races),
+ FunArgs = dialyzer_races:get_curr_fun_args(Races),
+ Code = lists:reverse(dialyzer_races:get_race_list(Races)),
+ ok = race_data_server_cast(
+ {renew_race_code, {Fun, FunArgs, Code}},
+ RaceDataServer),
+ CG.
+
+renew_race_code_handler({Fun, FunArgs, Code},
+ #race_data_state{race_code = RaceCode} = State) ->
+ State#race_data_state{race_code = dict:store(Fun, [FunArgs, Code], RaceCode)}.
+
+-spec renew_race_public_tables(label(), callgraph()) -> callgraph().
+
+renew_race_public_tables(VarLabel,
+ #callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok =
+ race_data_server_cast({renew_race_public_tables, VarLabel}, RaceDataServer),
+ CG.
+
+renew_race_public_tables_handler(VarLabel,
+ #race_data_state{public_tables = PT}
+ = State) ->
+ State#race_data_state{public_tables = ordsets:add_element(VarLabel, PT)}.
+
-spec cleanup(callgraph()) -> callgraph().
-cleanup(#callgraph{digraph = Digraph,
- name_map = NameMap,
- rev_name_map = RevNameMap,
- public_tables = PublicTables,
- named_tables = NamedTables,
- race_code = RaceCode}) ->
+cleanup(#callgraph{digraph = Digraph,
+ name_map = NameMap,
+ rev_name_map = RevNameMap,
+ race_data_server = RaceDataServer}) ->
#callgraph{digraph = Digraph,
- name_map = NameMap,
- rev_name_map = RevNameMap,
- public_tables = PublicTables,
- named_tables = NamedTables,
- race_code = RaceCode}.
+ name_map = NameMap,
+ rev_name_map = RevNameMap,
+ race_data_server = race_data_server_call(dup, RaceDataServer)}.
+
+-spec duplicate(callgraph()) -> callgraph().
+
+duplicate(#callgraph{race_data_server = RaceDataServer} = Callgraph) ->
+ Callgraph#callgraph{
+ race_data_server = race_data_server_call(dup, RaceDataServer)}.
+
+-spec dispose_race_server(callgraph()) -> ok.
+
+dispose_race_server(#callgraph{race_data_server = RaceDataServer}) ->
+ race_data_server_cast(stop, RaceDataServer).
-spec get_digraph(callgraph()) -> digraph().
@@ -633,28 +634,34 @@ get_digraph(#callgraph{digraph = Digraph}) ->
-spec get_named_tables(callgraph()) -> [string()].
-get_named_tables(#callgraph{named_tables = NamedTables}) ->
- NamedTables.
+get_named_tables(#callgraph{race_data_server = RaceDataServer}) ->
+ race_data_server_call(get_named_tables, RaceDataServer).
-spec get_public_tables(callgraph()) -> [label()].
-get_public_tables(#callgraph{public_tables = PT}) ->
- PT.
+get_public_tables(#callgraph{race_data_server = RaceDataServer}) ->
+ race_data_server_call(get_public_tables, RaceDataServer).
-spec get_race_code(callgraph()) -> dict().
-get_race_code(#callgraph{race_code = RaceCode}) ->
- RaceCode.
+get_race_code(#callgraph{race_data_server = RaceDataServer}) ->
+ race_data_server_call(get_race_code, RaceDataServer).
-spec get_race_detection(callgraph()) -> boolean().
get_race_detection(#callgraph{race_detection = RD}) ->
RD.
+-spec get_behaviour_api_calls(callgraph()) -> [{mfa(), mfa()}].
+
+get_behaviour_api_calls(#callgraph{race_data_server = RaceDataServer}) ->
+ race_data_server_call(get_behaviour_api_calls, RaceDataServer).
+
-spec race_code_new(callgraph()) -> callgraph().
-race_code_new(Callgraph) ->
- Callgraph#callgraph{race_code = dict:new()}.
+race_code_new(#callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok = race_data_server_cast(race_code_new, RaceDataServer),
+ CG.
-spec put_digraph(digraph(), callgraph()) -> callgraph().
@@ -663,8 +670,9 @@ put_digraph(Digraph, Callgraph) ->
-spec put_race_code(dict(), callgraph()) -> callgraph().
-put_race_code(RaceCode, Callgraph) ->
- Callgraph#callgraph{race_code = RaceCode}.
+put_race_code(RaceCode, #callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok = race_data_server_cast({put_race_code, RaceCode}, RaceDataServer),
+ CG.
-spec put_race_detection(boolean(), callgraph()) -> callgraph().
@@ -673,13 +681,79 @@ put_race_detection(RaceDetection, Callgraph) ->
-spec put_named_tables([string()], callgraph()) -> callgraph().
-put_named_tables(NamedTables, Callgraph) ->
- Callgraph#callgraph{named_tables = NamedTables}.
+put_named_tables(NamedTables,
+ #callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok = race_data_server_cast({put_named_tables, NamedTables}, RaceDataServer),
+ CG.
-spec put_public_tables([label()], callgraph()) -> callgraph().
-put_public_tables(PublicTables, Callgraph) ->
- Callgraph#callgraph{public_tables = PublicTables}.
+put_public_tables(PublicTables,
+ #callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok = race_data_server_cast({put_public_tables, PublicTables}, RaceDataServer),
+ CG.
+
+-spec put_behaviour_api_calls([{mfa(), mfa()}], callgraph()) -> callgraph().
+
+put_behaviour_api_calls(Calls,
+ #callgraph{race_data_server = RaceDataServer} = CG) ->
+ ok = race_data_server_cast({put_behaviour_api_calls, Calls}, RaceDataServer),
+ CG.
+
+
+new_race_data_server() ->
+ spawn_link(fun() -> race_data_server_loop(#race_data_state{}) end).
+
+race_data_server_loop(State) ->
+ receive
+ {call, From, Ref, Query} ->
+ Reply = race_data_server_handle_call(Query, State),
+ From ! {Ref, Reply},
+ race_data_server_loop(State);
+ {cast, stop} ->
+ ok;
+ {cast, Message} ->
+ NewState = race_data_server_handle_cast(Message, State),
+ race_data_server_loop(NewState)
+ end.
+
+race_data_server_call(Query, Server) ->
+ Ref = make_ref(),
+ Server ! {call, self(), Ref, Query},
+ receive
+ {Ref, Reply} -> Reply
+ end.
+
+race_data_server_cast(Message, Server) ->
+ Server ! {cast, Message},
+ ok.
+
+race_data_server_handle_cast(race_code_new, State) ->
+ State#race_data_state{race_code = dict:new()};
+race_data_server_handle_cast({Tag, Data}, State) ->
+ case Tag of
+ renew_race_info -> renew_race_info(Data, State);
+ renew_race_code -> renew_race_code_handler(Data, State);
+ renew_race_public_tables -> renew_race_public_tables_handler(Data, State);
+ put_race_code -> State#race_data_state{race_code = Data};
+ put_public_tables -> State#race_data_state{public_tables = Data};
+ put_named_tables -> State#race_data_state{named_tables = Data};
+ put_behaviour_api_calls -> State#race_data_state{beh_api_calls = Data}
+ end.
+
+race_data_server_handle_call(Query,
+ #race_data_state{race_code = RaceCode,
+ public_tables = PublicTables,
+ named_tables = NamedTables,
+ beh_api_calls = BehApiCalls}
+ = State) ->
+ case Query of
+ dup -> spawn_link(fun() -> race_data_server_loop(State) end);
+ get_race_code -> RaceCode;
+ get_public_tables -> PublicTables;
+ get_named_tables -> NamedTables;
+ get_behaviour_api_calls -> BehApiCalls
+ end.
%%=============================================================================
%% Utilities for 'dot'
@@ -695,7 +769,7 @@ to_dot(#callgraph{digraph = DG, esc = Esc} = CG, File) ->
end
end,
Escaping = [{Fun(L), {color, red}}
- || L <- sets:to_list(Esc), L =/= external],
+ || L <- [E || {E} <- ets:tab2list(Esc)], L =/= external],
Vertices = digraph_edges(DG),
hipe_dot:translate_list(Vertices, File, "CG", Escaping).
@@ -708,14 +782,41 @@ to_ps(#callgraph{} = CG, File, Args) ->
_ = os:cmd(Command),
ok.
-%-------------------------------------------------------------------------------
-
--spec put_behaviour_api_calls([{mfa(), mfa()}], callgraph()) -> callgraph().
-
-put_behaviour_api_calls(Calls, Callgraph) ->
- Callgraph#callgraph{beh_api_calls = Calls}.
-
--spec get_behaviour_api_calls(callgraph()) -> [{mfa(), mfa()}].
-
-get_behaviour_api_calls(Callgraph) ->
- Callgraph#callgraph.beh_api_calls.
+condensation(G) ->
+ SCs = digraph_utils:strong_components(G),
+ V2I = ets:new(condensation_v2i, []),
+ I2C = ets:new(condensation_i2c, []),
+ I2I = ets:new(condensation_i2i, [bag]),
+ CFun =
+ fun(SC, N) ->
+ lists:foreach(fun(V) -> true = ets:insert(V2I, {V,N}) end, SC),
+ true = ets:insert(I2C, {N, SC}),
+ N + 1
+ end,
+ lists:foldl(CFun, 1, SCs),
+ Fun1 =
+ fun({V1, V2}) ->
+ I1 = ets:lookup_element(V2I, V1, 2),
+ I2 = ets:lookup_element(V2I, V2, 2),
+ case I1 =:= I2 of
+ true -> true;
+ false -> ets:insert(I2I, {I1, I2})
+ end
+ end,
+ lists:foreach(Fun1, digraph:edges(G)),
+ Fun3 =
+ fun({I1, I2}, {Out, In}) ->
+ SC1 = ets:lookup_element(I2C, I1, 2),
+ SC2 = ets:lookup_element(I2C, I2, 2),
+ {dict:append(SC1, SC2, Out), dict:append(SC2, SC1, In)}
+ end,
+ {OutDict, InDict} = ets:foldl(Fun3, {dict:new(), dict:new()}, I2I),
+ [OutETS, InETS] =
+ [ets:new(Name,[{read_concurrency, true}]) ||
+ Name <- [callgraph_deps_out, callgraph_deps_in]],
+ ets:insert(OutETS, dict:to_list(OutDict)),
+ ets:insert(InETS, dict:to_list(InDict)),
+ ets:delete(V2I),
+ ets:delete(I2C),
+ ets:delete(I2I),
+ {{'e', OutETS, InETS}, SCs}.
diff --git a/lib/dialyzer/src/dialyzer_cl.erl b/lib/dialyzer/src/dialyzer_cl.erl
index 04a0db890f..5d253e77fa 100644
--- a/lib/dialyzer/src/dialyzer_cl.erl
+++ b/lib/dialyzer/src/dialyzer_cl.erl
@@ -188,6 +188,7 @@ plt_common(#options{init_plts = [InitPlt]} = Opts, RemoveFiles, AddFiles) ->
ok ->
case Opts#options.output_plt of
none -> ok;
+ InitPlt -> ok;
OutPlt ->
{ok, Binary} = file:read_file(InitPlt),
ok = file:write_file(OutPlt, Binary)
@@ -393,7 +394,8 @@ do_analysis(Files, Options, Plt, PltInfo) ->
defines = Options#options.defines,
include_dirs = Options#options.include_dirs,
files = Files,
- start_from = Options#options.from,
+ start_from = Options#options.from,
+ timing = Options#options.timing,
plt = Plt,
use_contracts = Options#options.use_contracts,
callgraph_file = Options#options.callgraph_file},
diff --git a/lib/dialyzer/src/dialyzer_cl_parse.erl b/lib/dialyzer/src/dialyzer_cl_parse.erl
index ff8fc39a5e..205b97ccf9 100644
--- a/lib/dialyzer/src/dialyzer_cl_parse.erl
+++ b/lib/dialyzer/src/dialyzer_cl_parse.erl
@@ -164,6 +164,13 @@ cl(["--src"|T]) ->
cl(["--no_spec"|T]) ->
put(dialyzer_options_use_contracts, false),
cl(T);
+cl(["--statistics"|T]) ->
+ put(dialyzer_timing, true),
+ cl(T);
+cl(["--resources"|T]) ->
+ put(dialyzer_options_report_mode, quiet),
+ put(dialyzer_timing, debug),
+ cl(T);
cl(["-v"|_]) ->
io:format("Dialyzer version "++?VSN++"\n"),
erlang:halt(?RET_NOTHING_SUSPICIOUS);
@@ -250,6 +257,7 @@ init() ->
put(dialyzer_output_format, formatted),
put(dialyzer_filename_opt, basename),
put(dialyzer_options_check_plt, DefaultOpts#options.check_plt),
+ put(dialyzer_timing, DefaultOpts#options.timing),
ok.
append_defines([Def, Val]) ->
@@ -290,6 +298,7 @@ cl_options() ->
{filename_opt, get(dialyzer_filename_opt)},
{analysis_type, get(dialyzer_options_analysis_type)},
{get_warnings, get(dialyzer_options_get_warnings)},
+ {timing, get(dialyzer_timing)},
{callgraph_file, get(dialyzer_callgraph_file)}
|common_options()].
@@ -351,7 +360,7 @@ help_message() ->
[--apps applications] [-o outfile]
[--build_plt] [--add_to_plt] [--remove_from_plt]
[--check_plt] [--no_check_plt] [--plt_info] [--get_warnings]
- [--no_native] [--fullpath]
+ [--no_native] [--fullpath] [--statistics]
Options:
files_or_dirs (for backwards compatibility also as: -c files_or_dirs)
Use Dialyzer from the command line to detect defects in the
@@ -418,6 +427,9 @@ Options:
Make Dialyzer a bit more quiet.
--verbose
Make Dialyzer a bit more verbose.
+ --statistics
+ Prints information about the progress of execution (analysis phases,
+ time spent in each and size of the relative input).
--build_plt
The analysis starts from an empty plt and creates a new one from the
files specified with -c and -r. Only works for beam files.
diff --git a/lib/dialyzer/src/dialyzer_codeserver.erl b/lib/dialyzer/src/dialyzer_codeserver.erl
index f1e87affbd..9989118671 100644
--- a/lib/dialyzer/src/dialyzer_codeserver.erl
+++ b/lib/dialyzer/src/dialyzer_codeserver.erl
@@ -52,9 +52,7 @@
new/0,
set_next_core_label/2,
set_temp_records/2,
- store_records/3,
store_temp_records/3,
- store_contracts/3,
store_temp_contracts/4]).
-export_type([codeserver/0]).
@@ -63,85 +61,159 @@
%%--------------------------------------------------------------------
--record(codeserver, {table_pid :: pid(),
- exported_types = sets:new() :: set(), % set(mfa())
- temp_exported_types = sets:new() :: set(), % set(mfa())
- exports = sets:new() :: set(), % set(mfa())
- next_core_label = 0 :: label(),
- records = dict:new() :: dict(),
- temp_records = dict:new() :: dict(),
- contracts = dict:new() :: dict(),
- callbacks = dict:new() :: dict(),
- temp_contracts = dict:new() :: dict(),
- temp_callbacks = dict:new() :: dict()
+-type dict_ets() :: ets:tid().
+-type set_ets() :: ets:tid().
+
+-record(codeserver, {next_core_label = 0 :: label(),
+ code :: dict_ets(),
+ exported_types :: set_ets(), % set(mfa())
+ records :: dict_ets(),
+ contracts :: dict_ets(),
+ callbacks :: dict_ets(),
+ exports :: 'clean' | set_ets(), % set(mfa())
+ temp_exported_types :: 'clean' | set_ets(), % set(mfa())
+ temp_records :: 'clean' | dict_ets(),
+ temp_contracts :: 'clean' | dict_ets(),
+ temp_callbacks :: 'clean' | dict_ets()
}).
-opaque codeserver() :: #codeserver{}.
%%--------------------------------------------------------------------
+ets_dict_find(Key, Table) ->
+ try ets:lookup_element(Table, Key, 2) of
+ Val -> {ok, Val}
+ catch
+ _:_ -> error
+ end.
+
+ets_dict_store(Key, Element, Table) ->
+ true = ets:insert(Table, {Key, Element}),
+ Table.
+
+ets_dict_store_dict(Dict, Table) ->
+ true = ets:insert(Table, dict:to_list(Dict)).
+
+ets_dict_to_dict(Table) ->
+ Fold = fun({Key,Value}, Dict) -> dict:store(Key, Value, Dict) end,
+ ets:foldl(Fold, dict:new(), Table).
+
+ets_set_is_element(Key, Table) ->
+ case ets:lookup(Table, Key) of
+ [] -> false;
+ _ -> true
+ end.
+
+ets_set_insert_set(Set, Table) ->
+ ets_set_insert_list(sets:to_list(Set), Table).
+
+ets_set_insert_list(List, Table) ->
+ true = ets:insert(Table, [{E} || E <- List]).
+
+ets_set_to_set(Table) ->
+ Fold = fun({E}, Set) -> sets:add_element(E, Set) end,
+ ets:foldl(Fold, sets:new(), Table).
+
+ets_read_concurrent_table(Name) ->
+ ets:new(Name,[{read_concurrency, true}]).
+
+%%--------------------------------------------------------------------
+
-spec new() -> codeserver().
new() ->
- #codeserver{table_pid = table__new()}.
+ CodeOptions = [compressed, public, {read_concurrency, true}],
+ Code = ets:new(dialyzer_codeserver_code, CodeOptions),
+ TempOptions = [public, {write_concurrency, true}],
+ [Exports, TempExportedTypes, TempRecords, TempContracts, TempCallbacks] =
+ [ets:new(Name, TempOptions) ||
+ Name <-
+ [dialyzer_codeserver_exports, dialyzer_codeserver_temp_exported_types,
+ dialyzer_codeserver_temp_records, dialyzer_codeserver_temp_contracts,
+ dialyzer_codeserver_temp_callbacks]],
+ #codeserver{code = Code,
+ exports = Exports,
+ temp_exported_types = TempExportedTypes,
+ temp_records = TempRecords,
+ temp_contracts = TempContracts,
+ temp_callbacks = TempCallbacks}.
-spec delete(codeserver()) -> 'ok'.
-delete(#codeserver{table_pid = TablePid}) ->
- table__delete(TablePid).
+delete(#codeserver{code = Code, exported_types = ExportedTypes,
+ records = Records, contracts = Contracts,
+ callbacks = Callbacks}) ->
+ lists:foreach(fun ets:delete/1,
+ [Code, ExportedTypes, Records, Contracts, Callbacks]).
-spec insert(atom(), cerl:c_module(), codeserver()) -> codeserver().
insert(Mod, ModCode, CS) ->
- NewTablePid = table__insert(CS#codeserver.table_pid, Mod, ModCode),
- CS#codeserver{table_pid = NewTablePid}.
+ Name = cerl:module_name(ModCode),
+ Exports = cerl:module_exports(ModCode),
+ Attrs = cerl:module_attrs(ModCode),
+ Defs = cerl:module_defs(ModCode),
+ As = cerl:get_ann(ModCode),
+ Funs =
+ [{{Mod, cerl:fname_id(Var), cerl:fname_arity(Var)},
+ Val} || Val = {Var, _Fun} <- Defs],
+ Keys = [Key || {Key, _Value} <- Funs],
+ ModEntry = {Mod, {Name, Exports, Attrs, Keys, As}},
+ true = ets:insert(CS#codeserver.code, [ModEntry|Funs]),
+ CS.
+
+-spec get_temp_exported_types(codeserver()) -> set().
+
+get_temp_exported_types(#codeserver{temp_exported_types = TempExpTypes}) ->
+ ets_set_to_set(TempExpTypes).
-spec insert_temp_exported_types(set(), codeserver()) -> codeserver().
insert_temp_exported_types(Set, CS) ->
- CS#codeserver{temp_exported_types = Set}.
+ TempExportedTypes = CS#codeserver.temp_exported_types,
+ true = ets_set_insert_set(Set, TempExportedTypes),
+ CS.
-spec insert_exports([mfa()], codeserver()) -> codeserver().
insert_exports(List, #codeserver{exports = Exports} = CS) ->
- Set = sets:from_list(List),
- NewExports = sets:union(Exports, Set),
- CS#codeserver{exports = NewExports}.
+ true = ets_set_insert_list(List, Exports),
+ CS.
-spec is_exported(mfa(), codeserver()) -> boolean().
is_exported(MFA, #codeserver{exports = Exports}) ->
- sets:is_element(MFA, Exports).
+ ets_set_is_element(MFA, Exports).
-spec get_exported_types(codeserver()) -> set(). % set(mfa())
get_exported_types(#codeserver{exported_types = ExpTypes}) ->
- ExpTypes.
-
--spec get_temp_exported_types(codeserver()) -> set().
-
-get_temp_exported_types(#codeserver{temp_exported_types = TempExpTypes}) ->
- TempExpTypes.
+ ets_set_to_set(ExpTypes).
-spec get_exports(codeserver()) -> set(). % set(mfa())
get_exports(#codeserver{exports = Exports}) ->
- Exports.
+ ets_set_to_set(Exports).
-spec finalize_exported_types(set(), codeserver()) -> codeserver().
finalize_exported_types(Set, CS) ->
- CS#codeserver{exported_types = Set, temp_exported_types = sets:new()}.
+ ExportedTypes = ets_read_concurrent_table(dialyzer_codeserver_exported_types),
+ true = ets_set_insert_set(Set, ExportedTypes),
+ TempExpTypes = CS#codeserver.temp_exported_types,
+ true = ets:delete(TempExpTypes),
+ CS#codeserver{exported_types = ExportedTypes, temp_exported_types = clean}.
-spec lookup_mod_code(atom(), codeserver()) -> cerl:c_module().
lookup_mod_code(Mod, CS) when is_atom(Mod) ->
- table__lookup(CS#codeserver.table_pid, Mod).
+ table__lookup(CS#codeserver.code, Mod).
-spec lookup_mfa_code(mfa(), codeserver()) -> {cerl:c_var(), cerl:c_fun()}.
lookup_mfa_code({_M, _F, _A} = MFA, CS) ->
- table__lookup(CS#codeserver.table_pid, MFA).
+ table__lookup(CS#codeserver.code, MFA).
-spec get_next_core_label(codeserver()) -> label().
@@ -153,20 +225,10 @@ get_next_core_label(#codeserver{next_core_label = NCL}) ->
set_next_core_label(NCL, CS) ->
CS#codeserver{next_core_label = NCL}.
--spec store_records(atom(), dict(), codeserver()) -> codeserver().
-
-store_records(Mod, Dict, #codeserver{records = RecDict} = CS)
- when is_atom(Mod) ->
- case dict:size(Dict) =:= 0 of
- true -> CS;
- false -> CS#codeserver{records = dict:store(Mod, Dict, RecDict)}
- end.
-
-spec lookup_mod_records(atom(), codeserver()) -> dict().
-lookup_mod_records(Mod, #codeserver{records = RecDict})
- when is_atom(Mod) ->
- case dict:find(Mod, RecDict) of
+lookup_mod_records(Mod, #codeserver{records = RecDict}) when is_atom(Mod) ->
+ case ets_dict_find(Mod, RecDict) of
error -> dict:new();
{ok, Dict} -> Dict
end.
@@ -174,7 +236,7 @@ lookup_mod_records(Mod, #codeserver{records = RecDict})
-spec get_records(codeserver()) -> dict().
get_records(#codeserver{records = RecDict}) ->
- RecDict.
+ ets_dict_to_dict(RecDict).
-spec store_temp_records(atom(), dict(), codeserver()) -> codeserver().
@@ -182,59 +244,58 @@ store_temp_records(Mod, Dict, #codeserver{temp_records = TempRecDict} = CS)
when is_atom(Mod) ->
case dict:size(Dict) =:= 0 of
true -> CS;
- false -> CS#codeserver{temp_records = dict:store(Mod, Dict, TempRecDict)}
+ false -> CS#codeserver{temp_records = ets_dict_store(Mod, Dict, TempRecDict)}
end.
-spec get_temp_records(codeserver()) -> dict().
get_temp_records(#codeserver{temp_records = TempRecDict}) ->
- TempRecDict.
+ ets_dict_to_dict(TempRecDict).
-spec set_temp_records(dict(), codeserver()) -> codeserver().
set_temp_records(Dict, CS) ->
- CS#codeserver{temp_records = Dict}.
+ true = ets:delete(CS#codeserver.temp_records),
+ TempRecords = ets:new(dialyzer_codeserver_temp_records,[]),
+ true = ets_dict_store_dict(Dict, TempRecords),
+ CS#codeserver{temp_records = TempRecords}.
-spec finalize_records(dict(), codeserver()) -> codeserver().
finalize_records(Dict, CS) ->
- CS#codeserver{records = Dict, temp_records = dict:new()}.
-
--spec store_contracts(atom(), dict(), codeserver()) -> codeserver().
-
-store_contracts(Mod, Dict, #codeserver{contracts = C} = CS) when is_atom(Mod) ->
- case dict:size(Dict) =:= 0 of
- true -> CS;
- false -> CS#codeserver{contracts = dict:store(Mod, Dict, C)}
- end.
+ true = ets:delete(CS#codeserver.temp_records),
+ Records = ets_read_concurrent_table(dialyzer_codeserver_records),
+ true = ets_dict_store_dict(Dict, Records),
+ CS#codeserver{records = Records, temp_records = clean}.
-spec lookup_mod_contracts(atom(), codeserver()) -> dict().
lookup_mod_contracts(Mod, #codeserver{contracts = ContDict})
when is_atom(Mod) ->
- case dict:find(Mod, ContDict) of
+ case ets_dict_find(Mod, ContDict) of
error -> dict:new();
- {ok, Dict} -> Dict
+ {ok, Keys} ->
+ dict:from_list([get_contract_pair(Key, ContDict)|| Key <- Keys])
end.
+get_contract_pair(Key, ContDict) ->
+ {Key, ets:lookup_element(ContDict, Key, 2)}.
+
-spec lookup_mfa_contract(mfa(), codeserver()) ->
'error' | {'ok', dialyzer_contracts:file_contract()}.
-lookup_mfa_contract({M,_F,_A} = MFA, #codeserver{contracts = ContDict}) ->
- case dict:find(M, ContDict) of
- error -> error;
- {ok, Dict} -> dict:find(MFA, Dict)
- end.
+lookup_mfa_contract(MFA, #codeserver{contracts = ContDict}) ->
+ ets_dict_find(MFA, ContDict).
-spec get_contracts(codeserver()) -> dict().
get_contracts(#codeserver{contracts = ContDict}) ->
- ContDict.
+ ets_dict_to_dict(ContDict).
--spec get_callbacks(codeserver()) -> dict().
+-spec get_callbacks(codeserver()) -> list().
get_callbacks(#codeserver{callbacks = CallbDict}) ->
- CallbDict.
+ ets:tab2list(CallbDict).
-spec store_temp_contracts(atom(), dict(), dict(), codeserver()) ->
codeserver().
@@ -246,91 +307,44 @@ store_temp_contracts(Mod, SpecDict, CallbackDict,
CS1 =
case dict:size(SpecDict) =:= 0 of
true -> CS;
- false -> CS#codeserver{temp_contracts = dict:store(Mod, SpecDict, Cn)}
+ false ->
+ CS#codeserver{temp_contracts = ets_dict_store(Mod, SpecDict, Cn)}
end,
case dict:size(CallbackDict) =:= 0 of
true -> CS1;
- false -> CS1#codeserver{temp_callbacks = dict:store(Mod, CallbackDict, Cb)}
+ false ->
+ CS1#codeserver{temp_callbacks = ets_dict_store(Mod, CallbackDict, Cb)}
end.
-spec get_temp_contracts(codeserver()) -> {dict(), dict()}.
get_temp_contracts(#codeserver{temp_contracts = TempContDict,
temp_callbacks = TempCallDict}) ->
- {TempContDict, TempCallDict}.
+ {ets_dict_to_dict(TempContDict), ets_dict_to_dict(TempCallDict)}.
-spec finalize_contracts(dict(), dict(), codeserver()) -> codeserver().
-finalize_contracts(CnDict, CbDict, CS) ->
- CS#codeserver{contracts = CnDict,
- callbacks = CbDict,
- temp_contracts = dict:new(),
- temp_callbacks = dict:new()
- }.
-
-table__new() ->
- spawn_link(fun() -> table__loop(none, dict:new()) end).
-
-table__delete(TablePid) ->
- TablePid ! stop,
- ok.
-
-table__lookup(TablePid, Key) ->
- TablePid ! {self(), lookup, Key},
- receive
- {TablePid, Key, Ans} -> Ans
- end.
-
-table__insert(TablePid, Key, Val) ->
- TablePid ! {insert, [{Key, term_to_binary(Val, [compressed])}]},
- TablePid.
-
-table__loop(Cached, Map) ->
- receive
- stop -> ok;
- {Pid, lookup, {M, F, A} = MFA} ->
- {NewCached, Ans} =
- case Cached of
- {M, Tree} ->
- Val = find_fun(F, A, Tree),
- {Cached, Val};
- _ ->
- Tree = fetch_and_expand(M, Map),
- Val = find_fun(F, A, Tree),
- {{M, Tree}, Val}
- end,
- Pid ! {self(), MFA, Ans},
- table__loop(NewCached, Map);
- {Pid, lookup, Mod} when is_atom(Mod) ->
- Ans = case Cached of
- {Mod, Tree} -> Tree;
- _ -> fetch_and_expand(Mod, Map)
- end,
- Pid ! {self(), Mod, Ans},
- table__loop({Mod, Ans}, Map);
- {insert, List} ->
- NewMap = lists:foldl(fun({Key, Val}, AccMap) ->
- dict:store(Key, Val, AccMap)
- end, Map, List),
- table__loop(Cached, NewMap)
- end.
-
-fetch_and_expand(Mod, Map) ->
- try
- Bin = dict:fetch(Mod, Map),
- binary_to_term(Bin)
- catch
- _:_ ->
- S = atom_to_list(Mod),
- Msg = "found no module named '" ++ S ++ "' in the analyzed files",
- exit({error, Msg})
- end.
-
-find_fun(F, A, Tree) ->
- Pred =
- fun({Var, _Fun}) ->
- (cerl:fname_id(Var) =/= F) orelse
- (cerl:fname_arity(Var) =/= A)
- end,
- [Val|_] = lists:dropwhile(Pred, cerl:module_defs(Tree)),
- Val.
+finalize_contracts(SpecDict, CallbackDict, CS) ->
+ Contracts = ets_read_concurrent_table(dialyzer_codeserver_contracts),
+ Callbacks = ets_read_concurrent_table(dialyzer_codeserver_callbacks),
+ Contracts = dict:fold(fun decompose_spec_dict/3, Contracts, SpecDict),
+ Callbacks = dict:fold(fun decompose_cb_dict/3, Callbacks, CallbackDict),
+ CS#codeserver{contracts = Contracts, callbacks = Callbacks,
+ temp_contracts = clean, temp_callbacks = clean}.
+
+decompose_spec_dict(Mod, Dict, Table) ->
+ Keys = dict:fetch_keys(Dict),
+ true = ets:insert(Table, dict:to_list(Dict)),
+ true = ets:insert(Table, {Mod, Keys}),
+ Table.
+
+decompose_cb_dict(_Mod, Dict, Table) ->
+ true = ets:insert(Table, dict:to_list(Dict)),
+ Table.
+
+table__lookup(TablePid, M) when is_atom(M) ->
+ {Name, Exports, Attrs, Keys, As} = ets:lookup_element(TablePid, M, 2),
+ Defs = [table__lookup(TablePid, Key) || Key <- Keys],
+ cerl:ann_c_module(As, Name, Exports, Attrs, Defs);
+table__lookup(TablePid, MFA) ->
+ ets:lookup_element(TablePid, MFA, 2).
diff --git a/lib/dialyzer/src/dialyzer_contracts.erl b/lib/dialyzer/src/dialyzer_contracts.erl
index 2b78b736ab..76f23d00b9 100644
--- a/lib/dialyzer/src/dialyzer_contracts.erl
+++ b/lib/dialyzer/src/dialyzer_contracts.erl
@@ -344,7 +344,7 @@ insert_constraints([{subtype, Type1, Type2}|Left], Dict) ->
false ->
%% A lot of things should change to add supertypes
throw({error, io_lib:format("First argument of is_subtype constraint "
- "must be a type variable\n", [])})
+ "must be a type variable: ~p\n", [Type1])})
end;
insert_constraints([], Dict) -> Dict.
@@ -385,9 +385,8 @@ contract_from_form([{type, _L1, bounded_fun,
RecDict, FileLine, TypeAcc, FormAcc) ->
TypeFun =
fun(ExpTypes, AllRecords) ->
- Constr1 = [constraint_from_form(C, RecDict, ExpTypes, AllRecords)
- || C <- Constr],
- VarDict = insert_constraints(Constr1, dict:new()),
+ {Constr1, VarDict} =
+ process_constraints(Constr, RecDict, ExpTypes, AllRecords),
Type = erl_types:t_from_form(Form, RecDict, VarDict),
NewType = erl_types:t_solve_remote(Type, ExpTypes, AllRecords),
{NewType, Constr1}
@@ -398,18 +397,66 @@ contract_from_form([{type, _L1, bounded_fun,
contract_from_form([], _RecDict, _FileLine, TypeAcc, FormAcc) ->
{lists:reverse(TypeAcc), lists:reverse(FormAcc)}.
-constraint_from_form({type, _, constraint, [{atom, _, is_subtype},
- [Type1, Type2]]}, RecDict,
- ExpTypes, AllRecords) ->
- T1 = erl_types:t_from_form(Type1, RecDict),
- T2 = erl_types:t_from_form(Type2, RecDict),
- T3 = erl_types:t_solve_remote(T1, ExpTypes, AllRecords),
- T4 = erl_types:t_solve_remote(T2, ExpTypes, AllRecords),
- {subtype, T3, T4};
-constraint_from_form({type, _, constraint, [{atom,_,Name}, List]}, _RecDict,
- _ExpTypes, _AllRecords) ->
- N = length(List),
- throw({error, io_lib:format("Unsupported type guard ~w/~w\n", [Name, N])}).
+process_constraints(Constrs, RecDict, ExpTypes, AllRecords) ->
+ Init = initialize_constraints(Constrs, RecDict, ExpTypes, AllRecords),
+ constraints_fixpoint(Init, RecDict, ExpTypes, AllRecords).
+
+initialize_constraints(Constrs, RecDict, ExpTypes, AllRecords) ->
+ initialize_constraints(Constrs, RecDict, ExpTypes, AllRecords, []).
+
+initialize_constraints([], _RecDict, _ExpTypes, _AllRecords, Acc) ->
+ Acc;
+initialize_constraints([Constr|Rest], RecDict, ExpTypes, AllRecords, Acc) ->
+ case Constr of
+ {type, _, constraint, [{atom, _, is_subtype}, [Type1, Type2]]} ->
+ T1 = final_form(Type1, RecDict, ExpTypes, AllRecords, dict:new()),
+ Entry = {T1, Type2},
+ initialize_constraints(Rest, RecDict, ExpTypes, AllRecords, [Entry|Acc]);
+ {type, _, constraint, [{atom,_,Name}, List]} ->
+ N = length(List),
+ throw({error,
+ io_lib:format("Unsupported type guard ~w/~w\n", [Name, N])})
+ end.
+
+constraints_fixpoint(Constrs, RecDict, ExpTypes, AllRecords) ->
+ VarDict =
+ constraints_to_dict(Constrs, RecDict, ExpTypes, AllRecords, dict:new()),
+ constraints_fixpoint(VarDict, Constrs, RecDict, ExpTypes, AllRecords).
+
+constraints_fixpoint(OldVarDict, Constrs, RecDict, ExpTypes, AllRecords) ->
+ NewVarDict =
+ constraints_to_dict(Constrs, RecDict, ExpTypes, AllRecords, OldVarDict),
+ case NewVarDict of
+ OldVarDict ->
+ DictFold =
+ fun(Key, Value, Acc) ->
+ [{subtype, erl_types:t_var(Key), Value}|Acc]
+ end,
+ FinalConstrs = dict:fold(DictFold, [], NewVarDict),
+ {FinalConstrs, NewVarDict};
+ _Other ->
+ constraints_fixpoint(NewVarDict, Constrs, RecDict, ExpTypes, AllRecords)
+ end.
+
+-define(TYPE_LIMIT, 4).
+
+final_form(Form, RecDict, ExpTypes, AllRecords, VarDict) ->
+ T1 = erl_types:t_from_form(Form, RecDict, VarDict),
+ T2 = erl_types:t_solve_remote(T1, ExpTypes, AllRecords),
+ erl_types:t_limit(T2, ?TYPE_LIMIT).
+
+constraints_to_dict(Constrs, RecDict, ExpTypes, AllRecords, VarDict) ->
+ Subtypes =
+ constraints_to_subs(Constrs, RecDict, ExpTypes, AllRecords, VarDict, []),
+ insert_constraints(Subtypes, dict:new()).
+
+constraints_to_subs([], _RecDict, _ExpTypes, _AllRecords, _VarDict, Acc) ->
+ Acc;
+constraints_to_subs([C|Rest], RecDict, ExpTypes, AllRecords, VarDict, Acc) ->
+ {T1, Form2} = C,
+ T2 = final_form(Form2, RecDict, ExpTypes, AllRecords, VarDict),
+ NewAcc = [{subtype, T1, T2}|Acc],
+ constraints_to_subs(Rest, RecDict, ExpTypes, AllRecords, VarDict, NewAcc).
%% Gets the most general domain of a list of domains of all
%% the overloaded contracts
diff --git a/lib/dialyzer/src/dialyzer_coordinator.erl b/lib/dialyzer/src/dialyzer_coordinator.erl
new file mode 100644
index 0000000000..5719132215
--- /dev/null
+++ b/lib/dialyzer/src/dialyzer_coordinator.erl
@@ -0,0 +1,250 @@
+%% -*- erlang-indent-level: 2 -*-
+%%-----------------------------------------------------------------------
+%% %CopyrightBegin%
+%%
+%% Copyright Ericsson AB 2006-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
+%% Erlang Public License along with this software. If not, it can be
+%% retrieved online at http://www.erlang.org/.
+%%
+%% Software distributed under the License is distributed on an "AS IS"
+%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+%% the License for the specific language governing rights and limitations
+%% under the License.
+%%
+%% %CopyrightEnd%
+%%
+
+%%%-------------------------------------------------------------------
+%%% File : dialyzer_coordinator.erl
+%%% Authors : Stavros Aronis <[email protected]>
+%%%-------------------------------------------------------------------
+
+-module(dialyzer_coordinator).
+
+%%% Export for dialyzer main process
+-export([parallel_job/4]).
+
+%%% Exports for all possible workers
+-export([wait_activation/0, job_done/3]).
+
+%%% Exports for the typesig and dataflow analysis workers
+-export([sccs_to_pids/2, request_activation/1]).
+
+%%% Exports for the compilation workers
+-export([get_next_label/2]).
+
+-export_type([coordinator/0, mode/0, init_data/0, result/0]).
+
+%%--------------------------------------------------------------------
+
+-type collector() :: pid().
+-type regulator() :: pid().
+-type scc_to_pid() :: ets:tid() | 'unused'.
+
+-type coordinator() :: {collector(), regulator(), scc_to_pid()}. %%opaque
+-type timing() :: dialyzer_timing:timing_server().
+
+-type scc() :: [mfa_or_funlbl()].
+-type mode() :: 'typesig' | 'dataflow' | 'compile' | 'warnings'.
+
+-type compile_jobs() :: [file:filename()].
+-type typesig_jobs() :: [scc()].
+-type dataflow_jobs() :: [module()].
+-type warnings_jobs() :: [module()].
+
+-type compile_init_data() :: dialyzer_analysis_callgraph:compile_init_data().
+-type typesig_init_data() :: dialyzer_succ_typings:typesig_init_data().
+-type dataflow_init_data() :: dialyzer_succ_typings:dataflow_init_data().
+-type warnings_init_data() :: dialyzer_succ_typings:warnings_init_data().
+
+-type compile_result() :: dialyzer_analysis_callgraph:compile_result().
+-type typesig_result() :: [mfa_or_funlbl()].
+-type dataflow_result() :: [mfa_or_funlbl()].
+-type warnings_result() :: [dial_warning()].
+
+-type init_data() :: compile_init_data() | typesig_init_data() |
+ dataflow_init_data() | warnings_init_data().
+
+-type result() :: compile_result() | typesig_result() |
+ dataflow_result() | warnings_result().
+
+-type job() :: scc() | module() | file:filename().
+-type job_result() :: dialyzer_analysis_callgraph:one_file_result() |
+ typesig_result() | dataflow_result() | warnings_result().
+
+-record(state, {mode :: mode(),
+ active = 0 :: integer(),
+ result :: result(),
+ next_label = 0 :: integer(),
+ init_data :: init_data(),
+ regulator :: regulator(),
+ scc_to_pid :: scc_to_pid()
+ }).
+
+-include("dialyzer.hrl").
+
+%%--------------------------------------------------------------------
+
+-spec parallel_job('compile', compile_jobs(), compile_init_data(), timing()) ->
+ {compile_result(), integer()};
+ ('typesig', typesig_jobs(), typesig_init_data(), timing()) ->
+ typesig_result();
+ ('dataflow', dataflow_jobs(), dataflow_init_data(),
+ timing()) -> dataflow_result();
+ ('warnings', warnings_jobs(), warnings_init_data(),
+ timing()) -> warnings_result().
+
+parallel_job(Mode, Jobs, InitData, Timing) ->
+ State = spawn_jobs(Mode, Jobs, InitData, Timing),
+ collect_result(State).
+
+spawn_jobs(Mode, Jobs, InitData, Timing) ->
+ Collector = self(),
+ Regulator = spawn_regulator(),
+ TypesigOrDataflow = (Mode =:= 'typesig') orelse (Mode =:= 'dataflow'),
+ SCCtoPID =
+ case TypesigOrDataflow of
+ true -> ets:new(scc_to_pid, [{read_concurrency, true}]);
+ false -> unused
+ end,
+ Coordinator = {Collector, Regulator, SCCtoPID},
+ Fold =
+ fun(Job, Count) ->
+ Pid = dialyzer_worker:launch(Mode, Job, InitData, Coordinator),
+ case TypesigOrDataflow of
+ true -> true = ets:insert(SCCtoPID, {Job, Pid});
+ false -> request_activation(Regulator, Pid)
+ end,
+ Count + 1
+ end,
+ JobCount = lists:foldl(Fold, 0, Jobs),
+ Unit =
+ case Mode of
+ 'typesig' -> "SCCs";
+ _ -> "modules"
+ end,
+ dialyzer_timing:send_size_info(Timing, JobCount, Unit),
+ InitResult =
+ case Mode of
+ 'compile' -> dialyzer_analysis_callgraph:compile_init_result();
+ _ -> []
+ end,
+ #state{mode = Mode, active = JobCount, result = InitResult, next_label = 0,
+ init_data = InitData, regulator = Regulator, scc_to_pid = SCCtoPID}.
+
+collect_result(#state{mode = Mode, active = Active, result = Result,
+ next_label = NextLabel, init_data = InitData,
+ regulator = Regulator, scc_to_pid = SCCtoPID} = State) ->
+ receive
+ {next_label_request, Estimation, Pid} ->
+ Pid ! {next_label_reply, NextLabel},
+ collect_result(State#state{next_label = NextLabel + Estimation});
+ {done, Job, Data} ->
+ NewResult = update_result(Mode, InitData, Job, Data, Result),
+ case Active of
+ 1 ->
+ kill_regulator(Regulator),
+ case Mode of
+ 'compile' ->
+ {NewResult, NextLabel};
+ X when X =:= 'typesig'; X =:= 'dataflow' ->
+ ets:delete(SCCtoPID),
+ NewResult;
+ 'warnings' ->
+ NewResult
+ end;
+ N ->
+ collect_result(State#state{result = NewResult, active = N - 1})
+ end
+ end.
+
+update_result(Mode, InitData, Job, Data, Result) ->
+ case Mode of
+ 'compile' ->
+ dialyzer_analysis_callgraph:add_to_result(Job, Data, Result,
+ InitData);
+ X when X =:= 'typesig'; X =:= 'dataflow' ->
+ dialyzer_succ_typings:lookup_names(Data, InitData) ++ Result;
+ 'warnings' ->
+ Data ++ Result
+ end.
+
+-spec sccs_to_pids([scc() | module()], coordinator()) ->
+ {[dialyzer_worker:worker()], [scc() | module()]}.
+
+sccs_to_pids(SCCs, {_Collector, _Regulator, SCCtoPID}) ->
+ Fold =
+ fun(SCC, {Pids, Unknown}) ->
+ try ets:lookup_element(SCCtoPID, SCC, 2) of
+ Result -> {[Result|Pids], Unknown}
+ catch
+ _:_ -> {Pids, [SCC|Unknown]}
+ end
+ end,
+ lists:foldl(Fold, {[], []}, SCCs).
+
+-spec job_done(job(), job_result(), coordinator()) -> ok.
+
+job_done(Job, Result, {Collector, Regulator, _SCCtoPID}) ->
+ Regulator ! done,
+ Collector ! {done, Job, Result},
+ ok.
+
+-spec get_next_label(integer(), coordinator()) -> integer().
+
+get_next_label(EstimatedSize, {Collector, _Regulator, _SCCtoPID}) ->
+ Collector ! {next_label_request, EstimatedSize, self()},
+ receive
+ {next_label_reply, NextLabel} -> NextLabel
+ end.
+
+-spec wait_activation() -> ok.
+
+wait_activation() ->
+ receive activate -> ok end.
+
+activate_pid(Pid) ->
+ Pid ! activate.
+
+-spec request_activation(coordinator()) -> ok.
+
+request_activation({_Collector, Regulator, _SCCtoPID}) ->
+ Regulator ! {req, self()},
+ wait_activation().
+
+request_activation(Regulator, Pid) ->
+ Regulator ! {req, Pid}.
+
+spawn_regulator() ->
+ InitTickets = dialyzer_utils:parallelism(),
+ spawn_link(fun() -> regulator_loop(InitTickets, queue:new()) end).
+
+regulator_loop(Tickets, Queue) ->
+ receive
+ {req, Pid} ->
+ case Tickets of
+ 0 ->
+ regulator_loop(0, queue:in(Pid, Queue));
+ N ->
+ activate_pid(Pid),
+ regulator_loop(N-1, Queue)
+ end;
+ done ->
+ {Waiting, NewQueue} = queue:out(Queue),
+ NewTickets =
+ case Waiting of
+ empty -> Tickets + 1;
+ {value, Pid} ->
+ activate_pid(Pid),
+ Tickets
+ end,
+ regulator_loop(NewTickets, NewQueue);
+ stop -> ok
+ end.
+
+kill_regulator(Regulator) ->
+ Regulator ! stop.
diff --git a/lib/dialyzer/src/dialyzer_dataflow.erl b/lib/dialyzer/src/dialyzer_dataflow.erl
index bd375b04fa..cb376daf68 100644
--- a/lib/dialyzer/src/dialyzer_dataflow.erl
+++ b/lib/dialyzer/src/dialyzer_dataflow.erl
@@ -32,13 +32,11 @@
%% Data structure interfaces.
-export([state__add_warning/2, state__cleanup/1,
+ state__duplicate/1, dispose_state/1,
state__get_callgraph/1, state__get_races/1,
state__get_records/1, state__put_callgraph/2,
state__put_races/2, state__records_only/1]).
-%% Debug and test interfaces.
--export([get_top_level_signatures/2, pp/1]).
-
-export_type([state/0]).
-include("dialyzer.hrl").
@@ -67,7 +65,7 @@
%%-define(DEBUG, true).
%%-define(DEBUG_PP, true).
-%%-define(DOT, true).
+%%-define(DEBUG_TIME, true).
-ifdef(DEBUG).
-import(erl_types, [t_to_string/1]).
@@ -111,7 +109,7 @@
-spec get_warnings(cerl:c_module(), dialyzer_plt:plt(),
dialyzer_callgraph:callgraph(), dict(), set()) ->
- {[dial_warning()], dict(), dict(), [label()], [string()]}.
+ {[dial_warning()], dict()}.
get_warnings(Tree, Plt, Callgraph, Records, NoWarnUnused) ->
State1 = analyze_module(Tree, Plt, Callgraph, Records, true),
@@ -119,145 +117,14 @@ get_warnings(Tree, Plt, Callgraph, Records, NoWarnUnused) ->
State3 =
state__renew_warnings(state__get_warnings(State2, NoWarnUnused), State2),
State4 = state__get_race_warnings(State3),
- Callgraph1 = State2#state.callgraph,
- {State4#state.warnings, state__all_fun_types(State4),
- dialyzer_callgraph:get_race_code(Callgraph1),
- dialyzer_callgraph:get_public_tables(Callgraph1),
- dialyzer_callgraph:get_named_tables(Callgraph1)}.
+ {State4#state.warnings, state__all_fun_types(State4)}.
-spec get_fun_types(cerl:c_module(), dialyzer_plt:plt(),
- dialyzer_callgraph:callgraph(), dict()) ->
- {dict(), dict(), [label()], [string()]}.
+ dialyzer_callgraph:callgraph(), dict()) -> dict().
get_fun_types(Tree, Plt, Callgraph, Records) ->
State = analyze_module(Tree, Plt, Callgraph, Records, false),
- Callgraph1 = State#state.callgraph,
- {state__all_fun_types(State),
- dialyzer_callgraph:get_race_code(Callgraph1),
- dialyzer_callgraph:get_public_tables(Callgraph1),
- dialyzer_callgraph:get_named_tables(Callgraph1)}.
-
-%%--------------------------------------------------------------------
-
--spec pp(file:filename()) -> 'ok'.
-
-pp(File) ->
- {ok, Code} = dialyzer_utils:get_core_from_src(File, [no_copt]),
- Plt = get_def_plt(),
- AnnTree = annotate_module(Code, Plt),
- io:put_chars(cerl_prettypr:format(AnnTree, [{hook, cerl_typean:pp_hook()}])),
- io:nl().
-
-%%--------------------------------------------------------------------
-%% This is used in the testsuite.
-
--spec get_top_level_signatures(cerl:c_module(), dict()) ->
- [{{atom(), arity()}, erl_types:erl_type()}].
-
-get_top_level_signatures(Code, Records) ->
- {Tree, _} = cerl_trees:label(cerl:from_records(Code)),
- Callgraph0 = dialyzer_callgraph:new(),
- Callgraph1 = dialyzer_callgraph:scan_core_tree(Tree, Callgraph0),
- {Callgraph2, _} = dialyzer_callgraph:remove_external(Callgraph1),
- Callgraph = dialyzer_callgraph:finalize(Callgraph2),
- to_dot(Callgraph),
- Plt = get_def_plt(),
- FunTypes = get_fun_types(Tree, Plt, Callgraph, Records),
- FunTypes1 = lists:foldl(fun({V, F}, Acc) ->
- Label = get_label(F),
- case dict:find(Label, Acc) of
- error ->
- Arity = cerl:fname_arity(V),
- Type = t_fun(lists:duplicate(Arity,
- t_none()),
- t_none()),
- dict:store(Label, Type, Acc);
- {ok, _} -> Acc
- end
- end, FunTypes, cerl:module_defs(Tree)),
- dialyzer_callgraph:delete(Callgraph),
- Sigs = [{{cerl:fname_id(V), cerl:fname_arity(V)},
- dict:fetch(get_label(F), FunTypes1)}
- || {V, F} <- cerl:module_defs(Tree)],
- ordsets:from_list(Sigs).
-
-get_def_plt() ->
- try
- dialyzer_plt:from_file(dialyzer_plt:get_default_plt())
- catch
- throw:{dialyzer_error, _} -> dialyzer_plt:new()
- end.
-
-%%% ===========================================================================
-%%%
-%%% Annotate all top level funs.
-%%%
-%%% ===========================================================================
-
-annotate_module(Code, Plt) ->
- {Tree, _} = cerl_trees:label(cerl:from_records(Code)),
- Callgraph0 = dialyzer_callgraph:new(),
- Callgraph1 = dialyzer_callgraph:scan_core_tree(Tree, Callgraph0),
- {Callgraph2, _} = dialyzer_callgraph:remove_external(Callgraph1),
- Callgraph = dialyzer_callgraph:finalize(Callgraph2),
- State = analyze_module(Tree, Plt, Callgraph),
- Res = annotate(Tree, State),
- dialyzer_callgraph:delete(Callgraph),
- Res.
-
-annotate(Tree, State) ->
- case cerl:subtrees(Tree) of
- [] -> set_type(Tree, State);
- List ->
- NewSubTrees = [[annotate(Subtree, State) || Subtree <- Group]
- || Group <- List],
- NewTree = cerl:update_tree(Tree, NewSubTrees),
- set_type(NewTree, State)
- end.
-
-set_type(Tree, State) ->
- case cerl:type(Tree) of
- 'fun' ->
- Type = state__fun_type(Tree, State),
- case t_is_any(Type) of
- true ->
- cerl:set_ann(Tree, delete_ann(typesig, cerl:get_ann(Tree)));
- false ->
- cerl:set_ann(Tree, append_ann(typesig, Type, cerl:get_ann(Tree)))
- end;
- apply ->
- case state__find_apply_return(Tree, State) of
- unknown -> Tree;
- ReturnType ->
- case t_is_any(ReturnType) of
- true ->
- cerl:set_ann(Tree, delete_ann(type, cerl:get_ann(Tree)));
- false ->
- cerl:set_ann(Tree, append_ann(type, ReturnType,
- cerl:get_ann(Tree)))
- end
- end;
- _ ->
- Tree
- end.
-
-append_ann(Tag, Val, [X | Xs]) ->
- if tuple_size(X) >= 1, element(1, X) =:= Tag ->
- append_ann(Tag, Val, Xs);
- true ->
- [X | append_ann(Tag, Val, Xs)]
- end;
-append_ann(Tag, Val, []) ->
- [{Tag, Val}].
-
-delete_ann(Tag, [X | Xs]) ->
- if tuple_size(X) >= 1, element(1, X) =:= Tag ->
- delete_ann(Tag, Xs);
- true ->
- [X | delete_ann(Tag, Xs)]
- end;
-delete_ann(_, []) ->
- [].
+ state__all_fun_types(State).
%%% ===========================================================================
%%%
@@ -265,56 +132,46 @@ delete_ann(_, []) ->
%%%
%%% ===========================================================================
-analyze_module(Tree, Plt, Callgraph) ->
- analyze_module(Tree, Plt, Callgraph, dict:new(), false).
-
analyze_module(Tree, Plt, Callgraph, Records, GetWarnings) ->
debug_pp(Tree, false),
Module = cerl:atom_val(cerl:module_name(Tree)),
RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
- RaceCode = dialyzer_callgraph:get_race_code(Callgraph),
BehaviourTranslations =
case RaceDetection of
true -> dialyzer_behaviours:translatable_behaviours(Tree);
false -> []
end,
TopFun = cerl:ann_c_fun([{label, top}], [], Tree),
- State = state__new(dialyzer_callgraph:race_code_new(Callgraph),
- TopFun, Plt, Module, Records, BehaviourTranslations),
+ State =
+ state__new(Callgraph, TopFun, Plt, Module, Records, BehaviourTranslations),
State1 = state__race_analysis(not GetWarnings, State),
State2 = analyze_loop(State1),
case GetWarnings of
true ->
State3 = state__set_warning_mode(State2),
State4 = analyze_loop(State3),
- State5 = state__restore_race_code(RaceCode, State4),
%% EXPERIMENTAL: Turn all behaviour API calls into calls to the
%% respective callback module's functions.
case BehaviourTranslations of
- [] -> dialyzer_races:race(State5);
+ [] -> dialyzer_races:race(State4);
Behaviours ->
- Callgraph2 = State5#state.callgraph,
- Digraph = dialyzer_callgraph:get_digraph(Callgraph2),
+ Digraph = dialyzer_callgraph:get_digraph(State4#state.callgraph),
TranslatedCallgraph =
dialyzer_behaviours:translate_callgraph(Behaviours, Module,
- Callgraph2),
+ Callgraph),
St =
- dialyzer_races:race(State5#state{callgraph = TranslatedCallgraph}),
- Callgraph3 = dialyzer_callgraph:put_digraph(Digraph,
- St#state.callgraph),
- St#state{callgraph = Callgraph3}
+ dialyzer_races:race(State4#state{callgraph = TranslatedCallgraph}),
+ FinalCallgraph = dialyzer_callgraph:put_digraph(Digraph,
+ St#state.callgraph),
+ St#state{callgraph = FinalCallgraph}
end;
false ->
- Callgraph1 = State2#state.callgraph,
- RaceCode1 = dialyzer_callgraph:get_race_code(Callgraph1),
- state__restore_race_code(
- dict:merge(fun (_K, V1, _V2) -> V1 end,
- RaceCode, RaceCode1), State2)
+ State2
end.
-analyze_loop(#state{callgraph = Callgraph, races = Races} = State) ->
+analyze_loop(State) ->
case state__get_work(State) of
none -> State;
{Fun, NewState1} ->
@@ -340,10 +197,9 @@ analyze_loop(#state{callgraph = Callgraph, races = Races} = State) ->
Map1 = enter_type_lists(Vars, ArgTypes, Map),
Body = cerl:fun_body(Fun),
FunLabel = get_label(Fun),
- RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
- RaceAnalysis = dialyzer_races:get_race_analysis(Races),
+ IsRaceAnalysisEnabled = is_race_analysis_enabled(State),
NewState3 =
- case RaceDetection andalso RaceAnalysis of
+ case IsRaceAnalysisEnabled of
true ->
NewState2 = state__renew_curr_fun(
state__lookup_name(FunLabel, NewState1), FunLabel,
@@ -357,17 +213,8 @@ analyze_loop(#state{callgraph = Callgraph, races = Races} = State) ->
[state__lookup_name(get_label(Fun), State),
t_to_string(t_fun(ArgTypes, BodyType))]),
NewState5 =
- case RaceDetection andalso RaceAnalysis of
- true ->
- Races1 = NewState4#state.races,
- Code = lists:reverse(dialyzer_races:get_race_list(Races1)),
- Callgraph1 =
- renew_code(dialyzer_races:get_curr_fun(Races1),
- dialyzer_races:get_curr_fun_args(Races1),
- Code,
- state__warning_mode(NewState4),
- NewState4#state.callgraph),
- NewState4#state{callgraph = Callgraph1};
+ case IsRaceAnalysisEnabled of
+ true -> renew_race_code(NewState4);
false -> NewState4
end,
NewState6 =
@@ -582,9 +429,7 @@ handle_apply_or_call([{local, external}|Left], Args, ArgTypes, Map, Tree, State,
ArgTypes, t_any());
handle_apply_or_call([{TypeOfApply, {Fun, Sig, Contr, LocalRet}}|Left],
Args, ArgTypes, Map, Tree,
- #state{callgraph = Callgraph, races = Races,
- opaques = Opaques} = State,
- AccArgTypes, AccRet) ->
+ #state{opaques = Opaques} = State, AccArgTypes, AccRet) ->
Any = t_any(),
AnyArgs = [Any || _ <- Args],
GenSig = {AnyArgs, fun(_) -> t_any() end},
@@ -680,8 +525,7 @@ handle_apply_or_call([{TypeOfApply, {Fun, Sig, Contr, LocalRet}}|Left],
?debug("ContrRet: ~s\n", [erl_types:t_to_string(CRange(TmpArgTypes))]),
?debug("SigRet: ~s\n", [erl_types:t_to_string(SigRange)]),
State1 =
- case dialyzer_callgraph:get_race_detection(Callgraph) andalso
- dialyzer_races:get_race_analysis(Races) of
+ case is_race_analysis_enabled(State) of
true ->
Ann = cerl:get_ann(Tree),
File = get_file(Ann),
@@ -1047,20 +891,17 @@ handle_call(Tree, Map, State) ->
%%----------------------------------------
-handle_case(Tree, Map, #state{callgraph = Callgraph} = State) ->
+handle_case(Tree, Map, State) ->
Arg = cerl:case_arg(Tree),
Clauses = filter_match_fail(cerl:case_clauses(Tree)),
{State1, Map1, ArgType} = SMA = traverse(Arg, Map, State),
case t_is_none_or_unit(ArgType) of
true -> SMA;
false ->
- Races = State1#state.races,
State2 =
- case dialyzer_callgraph:get_race_detection(Callgraph) andalso
- dialyzer_races:get_race_analysis(Races) of
+ case is_race_analysis_enabled(State) of
true ->
- RaceList = dialyzer_races:get_race_list(Races),
- RaceListSize = dialyzer_races:get_race_list_size(Races),
+ {RaceList, RaceListSize} = get_race_list_and_size(State1),
state__renew_race_list([beg_case|RaceList],
RaceListSize + 1, State1);
false -> State1
@@ -1094,9 +935,8 @@ handle_cons(Tree, Map, State) ->
%%----------------------------------------
-handle_let(Tree, Map, #state{callgraph = Callgraph, races = Races} = State) ->
- RaceAnalysis = dialyzer_races:get_race_analysis(Races),
- RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
+handle_let(Tree, Map, State) ->
+ IsRaceAnalysisEnabled = is_race_analysis_enabled(State),
Arg = cerl:let_arg(Tree),
Vars = cerl:let_vars(Tree),
{Map0, State0} =
@@ -1104,10 +944,9 @@ handle_let(Tree, Map, #state{callgraph = Callgraph, races = Races} = State) ->
true ->
[Var] = Vars,
{enter_subst(Var, Arg, Map),
- case RaceDetection andalso RaceAnalysis of
+ case IsRaceAnalysisEnabled of
true ->
- RaceList = dialyzer_races:get_race_list(Races),
- RaceListSize = dialyzer_races:get_race_list_size(Races),
+ {RaceList, RaceListSize} = get_race_list_and_size(State),
state__renew_race_list(
[dialyzer_races:let_tag_new(Var, Arg)|RaceList],
RaceListSize + 1, State);
@@ -1117,9 +956,8 @@ handle_let(Tree, Map, #state{callgraph = Callgraph, races = Races} = State) ->
end,
Body = cerl:let_body(Tree),
{State1, Map1, ArgTypes} = SMA = traverse(Arg, Map0, State0),
- Callgraph1 = State1#state.callgraph,
- Callgraph2 =
- case RaceDetection andalso RaceAnalysis andalso cerl:is_c_call(Arg) of
+ State2 =
+ case IsRaceAnalysisEnabled andalso cerl:is_c_call(Arg) of
true ->
Mod = cerl:call_module(Arg),
Name = cerl:call_name(Arg),
@@ -1127,16 +965,11 @@ handle_let(Tree, Map, #state{callgraph = Callgraph, races = Races} = State) ->
cerl:concrete(Mod) =:= ets andalso
cerl:is_literal(Name) andalso
cerl:concrete(Name) =:= new of
- true ->
- NewTable = dialyzer_races:get_new_table(State1#state.races),
- renew_public_tables(Vars, NewTable,
- state__warning_mode(State1),
- Callgraph1);
- false -> Callgraph1
+ true -> renew_race_public_tables(Vars, State1);
+ false -> State1
end;
- false -> Callgraph1
+ false -> State1
end,
- State2 = State1#state{callgraph = Callgraph2},
case t_is_none_or_unit(ArgTypes) of
true -> SMA;
false ->
@@ -1167,16 +1000,13 @@ handle_module(Tree, Map, State) ->
%%----------------------------------------
-handle_receive(Tree, Map,
- #state{callgraph = Callgraph, races = Races} = State) ->
+handle_receive(Tree, Map, State) ->
Clauses = filter_match_fail(cerl:receive_clauses(Tree)),
Timeout = cerl:receive_timeout(Tree),
State1 =
- case dialyzer_callgraph:get_race_detection(Callgraph) andalso
- dialyzer_races:get_race_analysis(Races) of
+ case is_race_analysis_enabled(State) of
true ->
- RaceList = dialyzer_races:get_race_list(Races),
- RaceListSize = dialyzer_races:get_race_list_size(Races),
+ {RaceList, RaceListSize} = get_race_list_and_size(State),
state__renew_race_list([beg_case|RaceList],
RaceListSize + 1, State);
false -> State
@@ -1299,16 +1129,13 @@ handle_tuple(Tree, Map, State) ->
%%----------------------------------------
%% Clauses
%%
-handle_clauses([C|Left], Arg, ArgType, OrigArgType,
- #state{callgraph = Callgraph, races = Races} = State,
- CaseTypes, MapIn, Acc, ClauseAcc) ->
- RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
- RaceAnalysis = dialyzer_races:get_race_analysis(Races),
+handle_clauses([C|Left], Arg, ArgType, OrigArgType, State, CaseTypes, MapIn,
+ Acc, ClauseAcc) ->
+ IsRaceAnalysisEnabled = is_race_analysis_enabled(State),
State1 =
- case RaceDetection andalso RaceAnalysis of
+ case IsRaceAnalysisEnabled of
true ->
- RaceList = dialyzer_races:get_race_list(Races),
- RaceListSize = dialyzer_races:get_race_list_size(Races),
+ {RaceList, RaceListSize} = get_race_list_and_size(State),
state__renew_race_list(
[dialyzer_races:beg_clause_new(Arg, cerl:clause_pats(C),
cerl:clause_guard(C))|
@@ -1319,11 +1146,9 @@ handle_clauses([C|Left], Arg, ArgType, OrigArgType,
{State2, ClauseMap, BodyType, NewArgType} =
do_clause(C, Arg, ArgType, OrigArgType, MapIn, State1),
{NewClauseAcc, State3} =
- case RaceDetection andalso RaceAnalysis of
+ case IsRaceAnalysisEnabled of
true ->
- Races1 = State2#state.races,
- RaceList1 = dialyzer_races:get_race_list(Races1),
- RaceListSize1 = dialyzer_races:get_race_list_size(Races1),
+ {RaceList1, RaceListSize1} = get_race_list_and_size(State2),
EndClause = dialyzer_races:end_clause_new(Arg, cerl:clause_pats(C),
cerl:clause_guard(C)),
{[EndClause|ClauseAcc],
@@ -1338,30 +1163,25 @@ handle_clauses([C|Left], Arg, ArgType, OrigArgType,
end,
handle_clauses(Left, Arg, NewArgType, OrigArgType, State3,
NewCaseTypes, MapIn, NewAcc, NewClauseAcc);
-handle_clauses([], _Arg, _ArgType, _OrigArgType,
- #state{callgraph = Callgraph, races = Races} = State,
- CaseTypes, _MapIn, Acc, ClauseAcc) ->
+handle_clauses([], _Arg, _ArgType, _OrigArgType, State, CaseTypes, _MapIn, Acc,
+ ClauseAcc) ->
State1 =
- case dialyzer_callgraph:get_race_detection(Callgraph) andalso
- dialyzer_races:get_race_analysis(Races) of
+ case is_race_analysis_enabled(State) of
true ->
+ {RaceList, RaceListSize} = get_race_list_and_size(State),
state__renew_race_list(
- [dialyzer_races:end_case_new(ClauseAcc)|
- dialyzer_races:get_race_list(Races)],
- dialyzer_races:get_race_list_size(Races) + 1, State);
+ [dialyzer_races:end_case_new(ClauseAcc)|RaceList],
+ RaceListSize + 1, State);
false -> State
end,
{lists:reverse(Acc), State1, t_sup(CaseTypes)}.
-do_clause(C, Arg, ArgType0, OrigArgType, Map,
- #state{callgraph = Callgraph, races = Races} = State) ->
+do_clause(C, Arg, ArgType0, OrigArgType, Map, State) ->
Pats = cerl:clause_pats(C),
Guard = cerl:clause_guard(C),
Body = cerl:clause_body(C),
- RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
- RaceAnalysis = dialyzer_races:get_race_analysis(Races),
State1 =
- case RaceDetection andalso RaceAnalysis of
+ case is_race_analysis_enabled(State) of
true ->
state__renew_fun_args(Pats, State);
false -> State
@@ -2914,10 +2734,6 @@ state__set_warning_mode(#state{tree_map = TreeMap, fun_tab = FunTab,
fun_tab = FunTab, warning_mode = true,
races = dialyzer_races:put_race_analysis(true, Races)}.
-state__restore_race_code(RaceCode, #state{callgraph = Callgraph} = State) ->
- State#state{callgraph = dialyzer_callgraph:put_race_code(RaceCode,
- Callgraph)}.
-
state__race_analysis(Analysis, #state{races = Races} = State) ->
State#state{races = dialyzer_races:put_race_analysis(Analysis, Races)}.
@@ -3260,21 +3076,6 @@ state__fun_info(Fun, #state{callgraph = CG, fun_tab = FunTab, plt = PLT}) ->
?debug("LocalRet: ~s\n", [t_to_string(LocalRet)]),
{Fun, Sig, Contract, LocalRet}.
-state__find_apply_return(Tree, #state{callgraph = Callgraph} = State) ->
- Apply = get_label(Tree),
- case dialyzer_callgraph:lookup_call_site(Apply, Callgraph) of
- error ->
- unknown;
- {ok, List} ->
- case lists:member(external, List) of
- true -> t_any();
- false ->
- FunTypes = [state__fun_type(F, State) || F <- List],
- Returns = [t_fun_range(F) || F <- FunTypes],
- t_sup(Returns)
- end
- end.
-
forward_args(Fun, ArgTypes, #state{work = Work, fun_tab = FunTab} = State) ->
{OldArgTypes, OldOut, Fixpoint} =
case dict:find(Fun, FunTab) of
@@ -3305,6 +3106,16 @@ state__cleanup(#state{callgraph = Callgraph,
races = dialyzer_races:cleanup(Races),
records = Records}.
+-spec state__duplicate(state()) -> state().
+
+state__duplicate(#state{callgraph = Callgraph} = State) ->
+ State#state{callgraph = dialyzer_callgraph:duplicate(Callgraph)}.
+
+-spec dispose_state(state()) -> ok.
+
+dispose_state(#state{callgraph = Callgraph}) ->
+ dialyzer_callgraph:dispose_race_server(Callgraph).
+
-spec state__get_callgraph(state()) -> dialyzer_callgraph:callgraph().
state__get_callgraph(#state{callgraph = Callgraph}) ->
@@ -3342,26 +3153,36 @@ state__records_only(#state{records = Records}) ->
%%%
%%% ===========================================================================
-renew_code(Fun, FunArgs, Code, WarningMode, Callgraph) ->
+is_race_analysis_enabled(#state{races = Races, callgraph = Callgraph}) ->
+ RaceDetection = dialyzer_callgraph:get_race_detection(Callgraph),
+ RaceAnalysis = dialyzer_races:get_race_analysis(Races),
+ RaceDetection andalso RaceAnalysis.
+
+get_race_list_and_size(#state{races = Races}) ->
+ dialyzer_races:get_race_list_and_size(Races).
+
+renew_race_code(#state{races = Races, callgraph = Callgraph,
+ warning_mode = WarningMode} = State) ->
case WarningMode of
- true -> Callgraph;
+ true -> State;
false ->
- RaceCode = dialyzer_callgraph:get_race_code(Callgraph),
- dialyzer_callgraph:put_race_code(
- dict:store(Fun, [FunArgs, Code], RaceCode), Callgraph)
+ NewCallgraph = dialyzer_callgraph:renew_race_code(Races, Callgraph),
+ State#state{callgraph = NewCallgraph}
end.
-renew_public_tables([Var], Table, WarningMode, Callgraph) ->
+renew_race_public_tables([Var], #state{races = Races, callgraph = Callgraph,
+ warning_mode = WarningMode} = State) ->
case WarningMode of
- true -> Callgraph;
+ true -> State;
false ->
+ Table = dialyzer_races:get_new_table(Races),
case Table of
- no_t -> Callgraph;
- _Other ->
- VarLabel = get_label(Var),
- PTables = dialyzer_callgraph:get_public_tables(Callgraph),
- dialyzer_callgraph:put_public_tables(
- lists:usort([VarLabel|PTables]), Callgraph)
+ no_t -> State;
+ _Other ->
+ VarLabel = get_label(Var),
+ NewCallgraph =
+ dialyzer_callgraph:renew_race_public_tables(VarLabel, Callgraph),
+ State#state{callgraph = NewCallgraph}
end
end.
@@ -3688,17 +3509,3 @@ strip_annotations(Tree) ->
debug_pp(_Tree, _UseHook) ->
ok.
-endif.
-
-%%----------------------------------------------------------------------------
-
--spec to_dot(dialyzer_callgraph:callgraph()) -> 'ok'.
-
--ifdef(DOT).
-to_dot(CG) ->
- dialyzer_callgraph:to_dot(CG).
--else.
-to_dot(_CG) ->
- ok.
--endif.
-
-%%----------------------------------------------------------------------------
diff --git a/lib/dialyzer/src/dialyzer_options.erl b/lib/dialyzer/src/dialyzer_options.erl
index 866650a0b2..a1e316d6cc 100644
--- a/lib/dialyzer/src/dialyzer_options.erl
+++ b/lib/dialyzer/src/dialyzer_options.erl
@@ -194,6 +194,8 @@ build_options([{OptionName, Value} = Term|Rest], Options) ->
callgraph_file ->
assert_filename(Value),
build_options(Rest, Options#options{callgraph_file = Value});
+ timing ->
+ build_options(Rest, Options#options{timing = Value});
_ ->
bad_option("Unknown dialyzer command line option", Term)
end;
diff --git a/lib/dialyzer/src/dialyzer_plt.erl b/lib/dialyzer/src/dialyzer_plt.erl
index 06eaadad9c..5f64099210 100644
--- a/lib/dialyzer/src/dialyzer_plt.erl
+++ b/lib/dialyzer/src/dialyzer_plt.erl
@@ -55,7 +55,10 @@
plt_and_info_from_file/1,
get_specs/1,
get_specs/4,
- to_file/4]).
+ to_file/4,
+ get_mini_plt/1,
+ restore_full_plt/2
+ ]).
%% Debug utilities
-export([pp_non_returning/0, pp_mod/1]).
@@ -82,7 +85,13 @@
contracts = table_new() :: dict(),
callbacks = table_new() :: dict(),
exported_types = sets:new() :: set()}).
--opaque plt() :: #plt{}.
+
+-record(mini_plt, {info :: ets:tid(),
+ contracts :: ets:tid(),
+ callbacks :: ets:tid()
+ }).
+
+-opaque plt() :: #plt{} | #mini_plt{}.
-include("dialyzer.hrl").
@@ -132,51 +141,48 @@ delete_list(#plt{info = Info, types = Types,
-spec insert_contract_list(plt(), dialyzer_contracts:plt_contracts()) -> plt().
-insert_contract_list(#plt{contracts = Contracts} = PLT, List) ->
- PLT#plt{contracts = table_insert_list(Contracts, List)}.
+insert_contract_list(#mini_plt{contracts = Contracts} = PLT, List) ->
+ true = ets:insert(Contracts, List),
+ PLT.
-spec insert_callbacks(plt(), dialyzer_codeserver:codeserver()) -> plt().
insert_callbacks(#plt{callbacks = Callbacks} = Plt, Codeserver) ->
- FunPreferNew = fun(_Key, _Val1, Val2) -> Val2 end,
- FunDictMerger =
- fun(_Key, Value, AccIn) -> dict:merge(FunPreferNew, Value, AccIn) end,
- MergedCallbacks = dict:fold(FunDictMerger, dict:new(),
- dialyzer_codeserver:get_callbacks(Codeserver)),
- List = dict:to_list(MergedCallbacks),
+ List = dialyzer_codeserver:get_callbacks(Codeserver),
Plt#plt{callbacks = table_insert_list(Callbacks, List)}.
-spec lookup_contract(plt(), mfa_patt()) -> 'none' | {'value', #contract{}}.
-lookup_contract(#plt{contracts = Contracts},
+lookup_contract(#mini_plt{contracts = ETSContracts},
{M, F, _} = MFA) when is_atom(M), is_atom(F) ->
- table_lookup(Contracts, MFA).
+ ets_table_lookup(ETSContracts, MFA).
-spec lookup_callbacks(plt(), module()) ->
- [{mfa(), {{Filename::string(), Line::pos_integer()}, #contract{}}}].
+ 'none' | {'value', [{mfa(), {{Filename::string(),
+ Line::pos_integer()},
+ #contract{}}}]}.
-lookup_callbacks(#plt{callbacks = Callbacks}, Mod) when is_atom(Mod) ->
- FunModFilter =
- fun({M, _F, _A}, _Val) -> M =:= Mod;
- ( _Key, _Val) -> false
- end,
- ModCallbacks = dict:filter(FunModFilter, Callbacks),
- dict:to_list(ModCallbacks).
+lookup_callbacks(#mini_plt{callbacks = ETSCallbacks}, Mod) when is_atom(Mod) ->
+ ets_table_lookup(ETSCallbacks, Mod).
-type ret_args_types() :: {erl_types:erl_type(), [erl_types:erl_type()]}.
-spec insert_list(plt(), [{mfa() | integer(), ret_args_types()}]) -> plt().
-insert_list(#plt{info = Info} = PLT, List) ->
- PLT#plt{info = table_insert_list(Info, List)}.
+insert_list(#mini_plt{info = Info} = PLT, List) ->
+ true = ets:insert(Info, List),
+ PLT.
-spec lookup(plt(), integer() | mfa_patt()) ->
'none' | {'value', ret_args_types()}.
-lookup(#plt{info = Info}, {M, F, _} = MFA) when is_atom(M), is_atom(F) ->
- table_lookup(Info, MFA);
-lookup(#plt{info = Info}, Label) when is_integer(Label) ->
- table_lookup(Info, Label).
+lookup(Plt, {M, F, _} = MFA) when is_atom(M), is_atom(F) ->
+ lookup_1(Plt, MFA);
+lookup(Plt, Label) when is_integer(Label) ->
+ lookup_1(Plt, Label).
+
+lookup_1(#mini_plt{info = Info}, MFAorLabel) ->
+ ets_table_lookup(Info, MFAorLabel).
-spec insert_types(plt(), dict()) -> plt().
@@ -503,6 +509,34 @@ init_md5_list_1([], DiffList, Acc) ->
init_md5_list_1(Md5List, [], Acc) ->
{ok, lists:reverse(Acc, Md5List)}.
+-spec get_mini_plt(plt()) -> plt().
+
+get_mini_plt(#plt{info = Info, contracts = Contracts, callbacks = Callbacks}) ->
+ [ETSInfo, ETSContracts, ETSCallbacks] =
+ [ets:new(Name, [public]) || Name <- [plt_info, plt_contracts, plt_callbacks]],
+ CallbackList = dict:to_list(Callbacks),
+ CallbacksByModule =
+ [{M, [Cb || {{M1,_,_},_} = Cb <- CallbackList, M1 =:= M]} ||
+ M <- lists:usort([M || {{M,_,_},_} <- CallbackList])],
+ [true, true] =
+ [ets:insert(ETS, dict:to_list(Data)) ||
+ {ETS, Data} <- [{ETSInfo, Info}, {ETSContracts, Contracts}]],
+ true = ets:insert(ETSCallbacks, CallbacksByModule),
+ #mini_plt{info = ETSInfo, contracts = ETSContracts, callbacks = ETSCallbacks};
+get_mini_plt(undefined) ->
+ undefined.
+
+-spec restore_full_plt(plt(), plt()) -> plt().
+
+restore_full_plt(#mini_plt{info = ETSInfo, contracts = ETSContracts}, Plt) ->
+ Info = dict:from_list(ets:tab2list(ETSInfo)),
+ Contracts = dict:from_list(ets:tab2list(ETSContracts)),
+ ets:delete(ETSContracts),
+ ets:delete(ETSInfo),
+ Plt#plt{info = Info, contracts = Contracts};
+restore_full_plt(undefined, undefined) ->
+ undefined.
+
%%---------------------------------------------------------------------------
%% Edoc
@@ -595,6 +629,13 @@ table_lookup(Plt, Obj) ->
{ok, Val} -> {value, Val}
end.
+ets_table_lookup(Plt, Obj) ->
+ try ets:lookup_element(Plt, Obj, 2) of
+ Val -> {value, Val}
+ catch
+ _:_ -> none
+ end.
+
table_lookup_module(Plt, Mod) ->
List = dict:fold(fun(Key, Val, Acc) ->
case Key of
diff --git a/lib/dialyzer/src/dialyzer_races.erl b/lib/dialyzer/src/dialyzer_races.erl
index cc635b0eef..cdb9f25999 100644
--- a/lib/dialyzer/src/dialyzer_races.erl
+++ b/lib/dialyzer/src/dialyzer_races.erl
@@ -36,6 +36,7 @@
-export([beg_clause_new/3, cleanup/1, end_case_new/1, end_clause_new/3,
get_curr_fun/1, get_curr_fun_args/1, get_new_table/1,
get_race_analysis/1, get_race_list/1, get_race_list_size/1,
+ get_race_list_and_size/1,
let_tag_new/2, new/0, put_curr_fun/3, put_fun_args/2,
put_race_analysis/2, put_race_list/3]).
@@ -346,6 +347,7 @@ fixup_race_list(RaceWarnTag, WarnVarArgs, State) ->
DepList2 =
fixup_race_list_helper(NewParents, Calls, CurrFun, WarnVarArgs,
RaceWarnTag, NewState),
+ dialyzer_dataflow:dispose_state(CleanState),
lists:usort(cleanup_dep_calls(DepList1 ++ DepList2)).
fixup_race_list_helper(Parents, Calls, CurrFun, WarnVarArgs, RaceWarnTag,
@@ -380,13 +382,15 @@ fixup_race_forward_pullout(CurrFun, CurrFunLabel, Calls, Code, RaceList,
InitFun, WarnVarArgs, RaceWarnTag, RaceVarMap,
FunDefVars, FunCallVars, FunArgTypes, NestingLevel,
State) ->
+ TState = dialyzer_dataflow:state__duplicate(State),
{DepList, NewCurrFun, NewCurrFunLabel, NewCalls,
NewCode, NewRaceList, NewRaceVarMap, NewFunDefVars,
NewFunCallVars, NewFunArgTypes, NewNestingLevel} =
fixup_race_forward(CurrFun, CurrFunLabel, Calls, Code, RaceList,
InitFun, WarnVarArgs, RaceWarnTag, RaceVarMap,
FunDefVars, FunCallVars, FunArgTypes, NestingLevel,
- cleanup_race_code(State)),
+ cleanup_race_code(TState)),
+ dialyzer_dataflow:dispose_state(TState),
case NewCode of
[] -> DepList;
[#fun_call{caller = NewCurrFun, callee = Call, arg_types = FunTypes,
@@ -2434,6 +2438,12 @@ get_race_list(#races{race_list = RaceList}) ->
get_race_list_size(#races{race_list_size = RaceListSize}) ->
RaceListSize.
+-spec get_race_list_and_size(races()) -> {code(), non_neg_integer()}.
+
+get_race_list_and_size(#races{race_list = RaceList,
+ race_list_size = RaceListSize}) ->
+ {RaceList, RaceListSize}.
+
-spec let_tag_new(var_to_map1(), var_to_map1()) -> #let_tag{}.
let_tag_new(Var, Arg) ->
diff --git a/lib/dialyzer/src/dialyzer_succ_typings.erl b/lib/dialyzer/src/dialyzer_succ_typings.erl
index 5982603b7b..9ca5a66dab 100644
--- a/lib/dialyzer/src/dialyzer_succ_typings.erl
+++ b/lib/dialyzer/src/dialyzer_succ_typings.erl
@@ -28,15 +28,22 @@
-module(dialyzer_succ_typings).
-export([analyze_callgraph/3,
- analyze_callgraph/4,
- get_warnings/6]).
+ analyze_callgraph/5,
+ get_warnings/7
+ ]).
-%% These are only intended as debug functions.
--export([doit/1,
- get_top_level_signatures/3]).
+-export([
+ find_succ_types_for_scc/2,
+ refine_one_module/2,
+ find_required_by/2,
+ find_depends_on/2,
+ collect_warnings/2,
+ lookup_names/2
+ ]).
+
+-export_type([typesig_init_data/0, dataflow_init_data/0, warnings_init_data/0]).
%%-define(DEBUG, true).
-%%-define(DEBUG_PP, true).
-ifdef(DEBUG).
-define(debug(X__, Y__), io:format(X__, Y__)).
@@ -54,11 +61,20 @@
%% State record -- local to this module
-type parent() :: 'none' | pid().
+-type typesig_init_data() :: term().
+-type dataflow_init_data() :: term().
+-type warnings_init_data() :: term().
+
+-type fixpoint_init_data() :: typesig_init_data() | dataflow_init_data().
+
+-type scc() :: [mfa_or_funlbl()] | [module()].
+
-record(st, {callgraph :: dialyzer_callgraph:callgraph(),
codeserver :: dialyzer_codeserver:codeserver(),
no_warn_unused :: set(),
parent = none :: parent(),
+ timing_server :: dialyzer_timing:timing_server(),
plt :: dialyzer_plt:plt()}).
%%--------------------------------------------------------------------
@@ -68,60 +84,89 @@
dialyzer_plt:plt().
analyze_callgraph(Callgraph, Plt, Codeserver) ->
- analyze_callgraph(Callgraph, Plt, Codeserver, none).
+ analyze_callgraph(Callgraph, Plt, Codeserver, none, none).
-spec analyze_callgraph(dialyzer_callgraph:callgraph(), dialyzer_plt:plt(),
- dialyzer_codeserver:codeserver(), parent()) ->
+ dialyzer_codeserver:codeserver(),
+ dialyzer_timing:timing_server(), parent()) ->
dialyzer_plt:plt().
-analyze_callgraph(Callgraph, Plt, Codeserver, Parent) ->
- State = #st{callgraph = Callgraph, plt = Plt,
- codeserver = Codeserver, parent = Parent},
- NewState = get_refined_success_typings(State),
- NewState#st.plt.
+analyze_callgraph(Callgraph, Plt, Codeserver, TimingServer, Parent) ->
+ NewState =
+ init_state_and_get_success_typings(Callgraph, Plt, Codeserver,
+ TimingServer, Parent),
+ dialyzer_plt:restore_full_plt(NewState#st.plt, Plt).
%%--------------------------------------------------------------------
-get_refined_success_typings(State) ->
- case find_succ_typings(State) of
+init_state_and_get_success_typings(Callgraph, Plt, Codeserver,
+ TimingServer, Parent) ->
+ {SCCs, Callgraph1} =
+ ?timing(TimingServer, "order", dialyzer_callgraph:finalize(Callgraph)),
+ State = #st{callgraph = Callgraph1, plt = dialyzer_plt:get_mini_plt(Plt),
+ codeserver = Codeserver, parent = Parent,
+ timing_server = TimingServer},
+ get_refined_success_typings(SCCs, State).
+
+get_refined_success_typings(SCCs, #st{callgraph = Callgraph,
+ timing_server = TimingServer} = State) ->
+ case find_succ_typings(SCCs, State) of
{fixpoint, State1} -> State1;
{not_fixpoint, NotFixpoint1, State1} ->
- Callgraph = State1#st.callgraph,
- NotFixpoint2 = [lookup_name(F, Callgraph) || F <- NotFixpoint1],
- ModulePostorder =
- dialyzer_callgraph:module_postorder_from_funs(NotFixpoint2, Callgraph),
- case refine_succ_typings(ModulePostorder, State1) of
+ {ModulePostorder, ModCallgraph} =
+ ?timing(
+ TimingServer, "order", _C1,
+ dialyzer_callgraph:module_postorder_from_funs(NotFixpoint1,
+ Callgraph)),
+ ModState = State1#st{callgraph = ModCallgraph},
+ case refine_succ_typings(ModulePostorder, ModState) of
{fixpoint, State2} ->
State2;
- {not_fixpoint, NotFixpoint3, State2} ->
- Callgraph1 = State2#st.callgraph,
+ {not_fixpoint, NotFixpoint2, State2} ->
%% Need to reset the callgraph.
- NotFixpoint4 = [lookup_name(F, Callgraph1) || F <- NotFixpoint3],
- Callgraph2 = dialyzer_callgraph:reset_from_funs(NotFixpoint4,
- Callgraph1),
- get_refined_success_typings(State2#st{callgraph = Callgraph2})
+ {NewSCCs, Callgraph2} =
+ ?timing(TimingServer, "order", _C2,
+ dialyzer_callgraph:reset_from_funs(NotFixpoint2,
+ ModCallgraph)),
+ NewState = State2#st{callgraph = Callgraph2},
+ get_refined_success_typings(NewSCCs, NewState)
end
end.
-type doc_plt() :: 'undefined' | dialyzer_plt:plt().
-spec get_warnings(dialyzer_callgraph:callgraph(), dialyzer_plt:plt(),
doc_plt(), dialyzer_codeserver:codeserver(), set(),
- pid()) ->
+ dialyzer_timing:timing_server(), pid()) ->
{[dial_warning()], dialyzer_plt:plt(), doc_plt()}.
-get_warnings(Callgraph, Plt, DocPlt, Codeserver, NoWarnUnused, Parent) ->
- InitState = #st{callgraph = Callgraph, codeserver = Codeserver,
- no_warn_unused = NoWarnUnused, parent = Parent, plt = Plt},
- NewState = get_refined_success_typings(InitState),
+get_warnings(Callgraph, Plt, DocPlt, Codeserver,
+ NoWarnUnused, TimingServer, Parent) ->
+ InitState =
+ init_state_and_get_success_typings(Callgraph, Plt, Codeserver,
+ TimingServer, Parent),
+ NewState = InitState#st{no_warn_unused = NoWarnUnused},
Mods = dialyzer_callgraph:modules(NewState#st.callgraph),
- CWarns = dialyzer_contracts:get_invalid_contract_warnings(Mods, Codeserver,
- NewState#st.plt),
- get_warnings_from_modules(Mods, NewState, DocPlt, CWarns).
-
-get_warnings_from_modules([M|Ms], State, DocPlt, Acc) when is_atom(M) ->
- send_log(State#st.parent, io_lib:format("Getting warnings for ~w\n", [M])),
+ MiniPlt = NewState#st.plt,
+ CWarns =
+ dialyzer_contracts:get_invalid_contract_warnings(Mods, Codeserver, MiniPlt),
+ MiniDocPlt = dialyzer_plt:get_mini_plt(DocPlt),
+ ModWarns =
+ ?timing(TimingServer, "warning",
+ get_warnings_from_modules(Mods, NewState, MiniDocPlt)),
+ {postprocess_warnings(CWarns ++ ModWarns, Codeserver),
+ dialyzer_plt:restore_full_plt(MiniPlt, Plt),
+ dialyzer_plt:restore_full_plt(MiniDocPlt, DocPlt)}.
+
+get_warnings_from_modules(Mods, State, DocPlt) ->
#st{callgraph = Callgraph, codeserver = Codeserver,
- no_warn_unused = NoWarnUnused, plt = Plt} = State,
+ no_warn_unused = NoWarnUnused, plt = Plt,
+ timing_server = TimingServer} = State,
+ Init = {Codeserver, Callgraph, NoWarnUnused, Plt, DocPlt},
+ dialyzer_coordinator:parallel_job(warnings, Mods, Init, TimingServer).
+
+-spec collect_warnings(module(), warnings_init_data()) -> [dial_warning()].
+
+collect_warnings(M, {Codeserver, Callgraph, NoWarnUnused, Plt, DocPlt}) ->
ModCode = dialyzer_codeserver:lookup_mod_code(M, Codeserver),
Records = dialyzer_codeserver:lookup_mod_records(M, Codeserver),
Contracts = dialyzer_codeserver:lookup_mod_contracts(M, Codeserver),
@@ -129,28 +174,27 @@ get_warnings_from_modules([M|Ms], State, DocPlt, Acc) when is_atom(M) ->
%% Check if there are contracts for functions that do not exist
Warnings1 =
dialyzer_contracts:contracts_without_fun(Contracts, AllFuns, Callgraph),
- {RawWarnings2, FunTypes, RaceCode, PublicTables, NamedTables} =
- dialyzer_dataflow:get_warnings(ModCode, Plt, Callgraph, Records, NoWarnUnused),
- {NewAcc, Warnings2} = postprocess_dataflow_warns(RawWarnings2, State, Acc),
+ {Warnings2, FunTypes} =
+ dialyzer_dataflow:get_warnings(ModCode, Plt, Callgraph,
+ Records, NoWarnUnused),
Attrs = cerl:module_attrs(ModCode),
- Warnings3 = dialyzer_behaviours:check_callbacks(M, Attrs, Plt, Codeserver),
- NewDocPlt = insert_into_doc_plt(FunTypes, Callgraph, DocPlt),
- NewCallgraph =
- dialyzer_callgraph:renew_race_info(Callgraph, RaceCode, PublicTables,
- NamedTables),
- State1 = st__renew_state_calls(NewCallgraph, State),
- get_warnings_from_modules(Ms, State1, NewDocPlt,
- [Warnings1, Warnings2, Warnings3|NewAcc]);
-get_warnings_from_modules([], #st{plt = Plt}, DocPlt, Acc) ->
- {lists:flatten(Acc), Plt, DocPlt}.
-
-postprocess_dataflow_warns(RawWarnings, State, WarnAcc) ->
- postprocess_dataflow_warns(RawWarnings, State, WarnAcc, []).
-
-postprocess_dataflow_warns([], _State, WAcc, Acc) ->
- {WAcc, lists:reverse(Acc)};
+ Warnings3 =
+ dialyzer_behaviours:check_callbacks(M, Attrs, Records, Plt, Codeserver),
+ DocPlt = insert_into_doc_plt(FunTypes, Callgraph, DocPlt),
+ lists:flatten([Warnings1, Warnings2, Warnings3]).
+
+postprocess_warnings(RawWarnings, Codeserver) ->
+ Pred =
+ fun({?WARN_CONTRACT_RANGE, _, _}) -> true;
+ (_) -> false
+ end,
+ {CRWarns, NonCRWarns} = lists:partition(Pred, RawWarnings),
+ postprocess_dataflow_warns(CRWarns, Codeserver, NonCRWarns, []).
+
+postprocess_dataflow_warns([], _Callgraph, WAcc, Acc) ->
+ lists:reverse(Acc, WAcc);
postprocess_dataflow_warns([{?WARN_CONTRACT_RANGE, {CallF, CallL}, Msg}|Rest],
- #st{codeserver = Codeserver} = State, WAcc, Acc) ->
+ Codeserver, WAcc, Acc) ->
{contract_range, [Contract, M, F, A, ArgStrings, CRet]} = Msg,
case dialyzer_codeserver:lookup_mfa_contract({M,F,A}, Codeserver) of
{ok, {{ContrF, _ContrL} = FileLine, _C}} ->
@@ -163,87 +207,65 @@ postprocess_dataflow_warns([{?WARN_CONTRACT_RANGE, {CallF, CallL}, Msg}|Rest],
(_) -> true
end,
FilterWAcc = lists:filter(Filter, WAcc),
- postprocess_dataflow_warns(Rest, State, FilterWAcc, [W|Acc]);
+ postprocess_dataflow_warns(Rest, Codeserver, FilterWAcc, [W|Acc]);
false ->
- postprocess_dataflow_warns(Rest, State, WAcc, Acc)
+ postprocess_dataflow_warns(Rest, Codeserver, WAcc, Acc)
end;
error ->
%% The contract is not in a module that is currently under analysis.
%% We display the warning in the file/line of the call.
NewMsg = {contract_range, [Contract, M, F, ArgStrings, CallL, CRet]},
W = {?WARN_CONTRACT_RANGE, {CallF, CallL}, NewMsg},
- postprocess_dataflow_warns(Rest, State, WAcc, [W|Acc])
- end;
-postprocess_dataflow_warns([W|Rest], State, Wacc, Acc) ->
- postprocess_dataflow_warns(Rest, State, Wacc, [W|Acc]).
+ postprocess_dataflow_warns(Rest, Codeserver, WAcc, [W|Acc])
+ end.
-refine_succ_typings(ModulePostorder, State) ->
- ?debug("Module postorder: ~p\n", [ModulePostorder]),
- refine_succ_typings(ModulePostorder, State, []).
-
-refine_succ_typings([SCC|SCCs], State, Fixpoint) ->
- Msg = io_lib:format("Dataflow of one SCC: ~w\n", [SCC]),
- send_log(State#st.parent, Msg),
- ?debug("~s\n", [Msg]),
- {NewState, FixpointFromScc} =
- case SCC of
- [M] -> refine_one_module(M, State);
- [_|_] -> refine_one_scc(SCC, State)
- end,
- NewFixpoint = ordsets:union(Fixpoint, FixpointFromScc),
- refine_succ_typings(SCCs, NewState, NewFixpoint);
-refine_succ_typings([], State, Fixpoint) ->
- case Fixpoint =:= [] of
+refine_succ_typings(Modules, #st{codeserver = Codeserver,
+ callgraph = Callgraph,
+ plt = Plt,
+ timing_server = Timing} = State) ->
+ ?debug("Module postorder: ~p\n", [Modules]),
+ Init = {Codeserver, Callgraph, Plt},
+ NotFixpoint =
+ ?timing(Timing, "refine",
+ dialyzer_coordinator:parallel_job(dataflow, Modules, Init, Timing)),
+ ?debug("==================== Dataflow done ====================\n\n", []),
+ case NotFixpoint =:= [] of
true -> {fixpoint, State};
- false -> {not_fixpoint, Fixpoint, State}
+ false -> {not_fixpoint, NotFixpoint, State}
end.
--spec refine_one_module(module(), #st{}) -> {#st{}, [label()]}. % ordset
+-spec find_depends_on(scc() | module(), fixpoint_init_data()) -> [scc()].
-refine_one_module(M, State) ->
- #st{callgraph = Callgraph, codeserver = CodeServer, plt = PLT} = State,
+find_depends_on(SCC, {_Codeserver, Callgraph, _Plt}) ->
+ dialyzer_callgraph:get_depends_on(SCC, Callgraph).
+
+-spec find_required_by(scc() | module(), fixpoint_init_data()) -> [scc()].
+
+find_required_by(SCC, {_Codeserver, Callgraph, _Plt}) ->
+ dialyzer_callgraph:get_required_by(SCC, Callgraph).
+
+-spec lookup_names([label()], fixpoint_init_data()) -> [mfa_or_funlbl()].
+
+lookup_names(Labels, {_Codeserver, Callgraph, _Plt}) ->
+ [lookup_name(F, Callgraph) || F <- Labels].
+
+-spec refine_one_module(module(), dataflow_init_data()) -> [label()]. % ordset
+
+refine_one_module(M, {CodeServer, Callgraph, Plt}) ->
ModCode = dialyzer_codeserver:lookup_mod_code(M, CodeServer),
AllFuns = collect_fun_info([ModCode]),
- FunTypes = get_fun_types_from_plt(AllFuns, Callgraph, PLT),
Records = dialyzer_codeserver:lookup_mod_records(M, CodeServer),
- {NewFunTypes, RaceCode, PublicTables, NamedTables} =
- dialyzer_dataflow:get_fun_types(ModCode, PLT, Callgraph, Records),
- NewCallgraph =
- dialyzer_callgraph:renew_race_info(Callgraph, RaceCode, PublicTables,
- NamedTables),
+ FunTypes = get_fun_types_from_plt(AllFuns, Callgraph, Plt),
+ NewFunTypes =
+ dialyzer_dataflow:get_fun_types(ModCode, Plt, Callgraph, Records),
case reached_fixpoint(FunTypes, NewFunTypes) of
- true ->
- State1 = st__renew_state_calls(NewCallgraph, State),
- {State1, ordsets:new()};
+ true -> [];
{false, NotFixpoint} ->
?debug("Not fixpoint\n", []),
- NewState = insert_into_plt(dict:from_list(NotFixpoint), State),
- NewState1 = st__renew_state_calls(NewCallgraph, NewState),
- {NewState1, ordsets:from_list([FunLbl || {FunLbl,_Type} <- NotFixpoint])}
+ Plt = insert_into_plt(dict:from_list(NotFixpoint), Callgraph, Plt),
+ [FunLbl || {FunLbl,_Type} <- NotFixpoint]
end.
-st__renew_state_calls(Callgraph, State) ->
- State#st{callgraph = Callgraph}.
-
-refine_one_scc(SCC, State) ->
- refine_one_scc(SCC, State, []).
-
-refine_one_scc(SCC, State, AccFixpoint) ->
- {NewState, FixpointFromScc} = refine_mods_in_scc(SCC, State, []),
- case FixpointFromScc =:= [] of
- true -> {NewState, AccFixpoint};
- false ->
- NewAccFixpoint = ordsets:union(AccFixpoint, FixpointFromScc),
- refine_one_scc(SCC, NewState, NewAccFixpoint)
- end.
-
-refine_mods_in_scc([Mod|Mods], State, Fixpoint) ->
- {NewState, FixpointFromModule} = refine_one_module(Mod, State),
- NewFixpoint = ordsets:union(FixpointFromModule, Fixpoint),
- refine_mods_in_scc(Mods, NewState, NewFixpoint);
-refine_mods_in_scc([], State, Fixpoint) ->
- {State, Fixpoint}.
-
reached_fixpoint(OldTypes, NewTypes) ->
reached_fixpoint(OldTypes, NewTypes, false).
@@ -299,31 +321,21 @@ compare_types_1([], [], _Strict, NotFixpoint) ->
false -> {false, NotFixpoint}
end.
-find_succ_typings(State) ->
- find_succ_typings(State, []).
-
-find_succ_typings(#st{callgraph = Callgraph, parent = Parent} = State,
- NotFixpoint) ->
- case dialyzer_callgraph:take_scc(Callgraph) of
- {ok, SCC, NewCallgraph} ->
- Msg = io_lib:format("Typesig analysis for SCC: ~w\n", [format_scc(SCC)]),
- ?debug("~s", [Msg]),
- send_log(Parent, Msg),
- {NewState, NewNotFixpoint1} =
- analyze_scc(SCC, State#st{callgraph = NewCallgraph}),
- NewNotFixpoint2 = ordsets:union(NewNotFixpoint1, NotFixpoint),
- find_succ_typings(NewState, NewNotFixpoint2);
- none ->
- ?debug("==================== Typesig done ====================\n\n", []),
- case NotFixpoint =:= [] of
- true -> {fixpoint, State};
- false -> {not_fixpoint, NotFixpoint, State}
- end
+find_succ_typings(SCCs, #st{codeserver = Codeserver, callgraph = Callgraph,
+ plt = Plt, timing_server = Timing} = State) ->
+ Init = {Codeserver, Callgraph, Plt},
+ NotFixpoint =
+ ?timing(Timing, "typesig",
+ dialyzer_coordinator:parallel_job(typesig, SCCs, Init, Timing)),
+ ?debug("==================== Typesig done ====================\n\n", []),
+ case NotFixpoint =:= [] of
+ true -> {fixpoint, State};
+ false -> {not_fixpoint, NotFixpoint, State}
end.
-analyze_scc(SCC, #st{codeserver = Codeserver,
- callgraph = Callgraph,
- plt = Plt} = State) ->
+-spec find_succ_types_for_scc(scc(), typesig_init_data()) -> [mfa_or_funlbl()].
+
+find_succ_types_for_scc(SCC, {Codeserver, Callgraph, Plt}) ->
SCC_Info = [{MFA,
dialyzer_codeserver:lookup_mfa_code(MFA, Codeserver),
dialyzer_codeserver:lookup_mod_records(M, Codeserver)}
@@ -332,26 +344,18 @@ analyze_scc(SCC, #st{codeserver = Codeserver,
|| {_, _, _} = MFA <- SCC],
Contracts2 = [{MFA, Contract} || {MFA, {ok, Contract}} <- Contracts1],
Contracts3 = orddict:from_list(Contracts2),
- NextLabel = dialyzer_codeserver:get_next_core_label(Codeserver),
- {SuccTypes, PltContracts, NotFixpoint} =
- find_succ_types_for_scc(SCC_Info, Contracts3, NextLabel, Callgraph, Plt),
- State1 = insert_into_plt(SuccTypes, State),
- ContrPlt = dialyzer_plt:insert_contract_list(State1#st.plt, PltContracts),
- {State1#st{plt = ContrPlt}, NotFixpoint}.
-
-find_succ_types_for_scc(SCC_Info, Contracts, NextLabel, Callgraph, Plt) ->
- %% Assume that the PLT contains the current propagated types
+ Label = dialyzer_codeserver:get_next_core_label(Codeserver),
AllFuns = collect_fun_info([Fun || {_MFA, {_Var, Fun}, _Rec} <- SCC_Info]),
PropTypes = get_fun_types_from_plt(AllFuns, Callgraph, Plt),
- FunTypes = dialyzer_typesig:analyze_scc(SCC_Info, NextLabel,
- Callgraph, Plt, PropTypes),
+ %% Assume that the PLT contains the current propagated types
+ FunTypes =
+ dialyzer_typesig:analyze_scc(SCC_Info, Label, Callgraph, Plt, PropTypes),
AllFunSet = sets:from_list([X || {X, _} <- AllFuns]),
- FilteredFunTypes = dict:filter(fun(X, _) ->
- sets:is_element(X, AllFunSet)
- end, FunTypes),
+ FilteredFunTypes =
+ dict:filter(fun(X, _) -> sets:is_element(X, AllFunSet) end, FunTypes),
%% Check contracts
- PltContracts = dialyzer_contracts:check_contracts(Contracts, Callgraph,
- FilteredFunTypes),
+ PltContracts =
+ dialyzer_contracts:check_contracts(Contracts3, Callgraph, FilteredFunTypes),
ContractFixpoint =
lists:all(fun({MFA, _C}) ->
%% Check the non-deleted PLT
@@ -360,14 +364,14 @@ find_succ_types_for_scc(SCC_Info, Contracts, NextLabel, Callgraph, Plt) ->
{value, _} -> true
end
end, PltContracts),
+ Plt = insert_into_plt(FilteredFunTypes, Callgraph, Plt),
+ Plt = dialyzer_plt:insert_contract_list(Plt, PltContracts),
case (ContractFixpoint andalso
reached_fixpoint_strict(PropTypes, FilteredFunTypes)) of
- true ->
- {FilteredFunTypes, PltContracts, []};
+ true -> [];
false ->
?debug("Not fixpoint for: ~w\n", [AllFuns]),
- {FilteredFunTypes, PltContracts,
- ordsets:from_list([Fun || {Fun, _Arity} <- AllFuns])}
+ [Fun || {Fun, _Arity} <- AllFuns]
end.
get_fun_types_from_plt(FunList, Callgraph, Plt) ->
@@ -407,10 +411,10 @@ insert_into_doc_plt(FunTypes, Callgraph, DocPlt) ->
SuccTypes = format_succ_types(FunTypes, Callgraph),
dialyzer_plt:insert_list(DocPlt, SuccTypes).
-insert_into_plt(SuccTypes0, #st{callgraph = Callgraph, plt = Plt} = State) ->
+insert_into_plt(SuccTypes0, Callgraph, Plt) ->
SuccTypes = format_succ_types(SuccTypes0, Callgraph),
debug_pp_succ_typings(SuccTypes),
- State#st{plt = dialyzer_plt:insert_list(Plt, SuccTypes)}.
+ dialyzer_plt:insert_list(Plt, SuccTypes).
format_succ_types(SuccTypes, Callgraph) ->
format_succ_types(dict:to_list(SuccTypes), Callgraph, []).
@@ -445,131 +449,3 @@ lookup_name(F, CG) ->
error -> F;
{ok, Name} -> Name
end.
-
-send_log(none, _Msg) ->
- ok;
-send_log(Parent, Msg) ->
- Parent ! {self(), log, lists:flatten(Msg)},
- ok.
-
-format_scc(SCC) ->
- [MFA || {_M, _F, _A} = MFA <- SCC].
-
-%% ============================================================================
-%%
-%% Debug interface.
-%%
-%% ============================================================================
-
--spec doit(atom() | file:filename()) -> 'ok'.
-
-doit(Module) ->
- {ok, AbstrCode} = dialyzer_utils:get_abstract_code_from_src(Module),
- {ok, Code} = dialyzer_utils:get_core_from_abstract_code(AbstrCode),
- {ok, Records} = dialyzer_utils:get_record_and_type_info(AbstrCode),
- %% contract typing info in dictionary format
- {ok, Contracts, _Callbacks} =
- dialyzer_utils:get_spec_info(cerl:concrete(cerl:module_name(Code)),
- AbstrCode, Records),
- Sigs0 = get_top_level_signatures(Code, Records, Contracts),
- M = if is_atom(Module) ->
- list_to_atom(filename:basename(atom_to_list(Module)));
- is_list(Module) ->
- list_to_atom(filename:basename(Module))
- end,
- Sigs1 = [{{M, F, A}, Type} || {{F, A}, Type} <- Sigs0],
- Sigs = ordsets:from_list(Sigs1),
- io:format("==================== Final result ====================\n\n", []),
- pp_signatures(Sigs, Records),
- ok.
-
--spec get_top_level_signatures(cerl:c_module(), dict(), dict()) ->
- [{{atom(), arity()}, erl_types:erl_type()}].
-
-get_top_level_signatures(Code, Records, Contracts) ->
- Tree = cerl:from_records(Code),
- {LabeledTree, NextLabel} = cerl_trees:label(Tree),
- Plt = get_def_plt(),
- ModuleName = cerl:atom_val(cerl:module_name(LabeledTree)),
- Plt1 = dialyzer_plt:delete_module(Plt, ModuleName),
- Plt2 = analyze_module(LabeledTree, NextLabel, Plt1, Records, Contracts),
- M = cerl:concrete(cerl:module_name(Tree)),
- Functions = [{M, cerl:fname_id(V), cerl:fname_arity(V)}
- || {V, _F} <- cerl:module_defs(LabeledTree)],
- %% First contracts check
- AllContracts = dict:fetch_keys(Contracts),
- ErrorContracts = AllContracts -- Functions,
- lists:foreach(fun(C) ->
- io:format("Contract for non-existing function: ~w\n",[C])
- end, ErrorContracts),
- Types = [{MFA, dialyzer_plt:lookup(Plt2, MFA)} || MFA <- Functions],
- Sigs = [{{F, A}, erl_types:t_fun(ArgT, RetT)}
- || {{_M, F, A}, {value, {RetT, ArgT}}} <- Types],
- ordsets:from_list(Sigs).
-
-get_def_plt() ->
- try
- dialyzer_plt:from_file(dialyzer_plt:get_default_plt())
- catch
- error:no_such_file -> dialyzer_plt:new();
- throw:{dialyzer_error, _} -> dialyzer_plt:new()
- end.
-
-pp_signatures([{{_, module_info, 0}, _}|Left], Records) ->
- pp_signatures(Left, Records);
-pp_signatures([{{_, module_info, 1}, _}|Left], Records) ->
- pp_signatures(Left, Records);
-pp_signatures([{{M, F, _A}, Type}|Left], Records) ->
- TypeString =
- case cerl:is_literal(Type) of
-%% Commented out so that dialyzer does not complain
-%% false ->
-%% "fun(" ++ String = erl_types:t_to_string(Type, Records),
-%% string:substr(String, 1, length(String)-1);
- true ->
- io_lib:format("~w", [cerl:concrete(Type)])
- end,
- io:format("~w:~w~s\n", [M, F, TypeString]),
- pp_signatures(Left, Records);
-pp_signatures([], _Records) ->
- ok.
-
--ifdef(DEBUG_PP).
-debug_pp(Tree, _Map) ->
- Tree1 = strip_annotations(Tree),
- io:put_chars(cerl_prettypr:format(Tree1)),
- io:nl().
-
-strip_annotations(Tree) ->
- cerl_trees:map(fun(T) ->
- case cerl:is_literal(T) orelse cerl:is_c_values(T) of
- true -> cerl:set_ann(T, []);
- false ->
- Label = cerl_trees:get_label(T),
- cerl:set_ann(T, [{'label', Label}])
- end
- end, Tree).
--else.
-debug_pp(_Tree, _Map) ->
- ok.
--endif. % DEBUG_PP
-
-%%
-%% Analysis of a single module
-%%
-analyze_module(LabeledTree, NextLbl, Plt, Records, Contracts) ->
- debug_pp(LabeledTree, dict:new()),
- CallGraph1 = dialyzer_callgraph:new(),
- CallGraph2 = dialyzer_callgraph:scan_core_tree(LabeledTree, CallGraph1),
- {CallGraph3, _Ext} = dialyzer_callgraph:remove_external(CallGraph2),
- CallGraph4 = dialyzer_callgraph:finalize(CallGraph3),
- CodeServer1 = dialyzer_codeserver:new(),
- Mod = cerl:concrete(cerl:module_name(LabeledTree)),
- CodeServer2 = dialyzer_codeserver:insert(Mod, LabeledTree, CodeServer1),
- CodeServer3 = dialyzer_codeserver:set_next_core_label(NextLbl, CodeServer2),
- CodeServer4 = dialyzer_codeserver:store_records(Mod, Records, CodeServer3),
- CodeServer5 = dialyzer_codeserver:store_contracts(Mod, Contracts, CodeServer4),
- Res = analyze_callgraph(CallGraph4, Plt, CodeServer5),
- dialyzer_callgraph:delete(CallGraph4),
- dialyzer_codeserver:delete(CodeServer5),
- Res.
diff --git a/lib/dialyzer/src/dialyzer_timing.erl b/lib/dialyzer/src/dialyzer_timing.erl
new file mode 100644
index 0000000000..b1a4bdc07c
--- /dev/null
+++ b/lib/dialyzer/src/dialyzer_timing.erl
@@ -0,0 +1,133 @@
+%% -*- erlang-indent-level: 2 -*-
+%%-------------------------------------------------------------------
+%% %CopyrightBegin%
+%%
+%% Copyright Ericsson AB 2006-2012. 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
+%% Erlang Public License along with this software. If not, it can be
+%% retrieved online at http://www.erlang.org/.
+%%
+%% Software distributed under the License is distributed on an "AS IS"
+%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+%% the License for the specific language governing rights and limitations
+%% under the License.
+%%
+%% %CopyrightEnd%
+%%
+
+%%%-------------------------------------------------------------------
+%%% File : dialyzer_timing.erl
+%%% Authors : Stavros Aronis <[email protected]>
+%%% Description : Timing reports for Dialyzer
+%%%-------------------------------------------------------------------
+
+-module(dialyzer_timing).
+
+-export([init/1, start_stamp/2, send_size_info/3, end_stamp/1, stop/1]).
+
+-export_type([timing_server/0]).
+
+-type timing_server() :: pid() | 'none'.
+
+-spec init(boolean() | 'debug') -> timing_server().
+
+init(Active) ->
+ case Active of
+ true ->
+ io:format("\n"),
+ spawn_link(fun() -> loop(now(), 0, "") end);
+ debug ->
+ io:format("\n"),
+ spawn_link(fun() -> debug_loop("") end);
+ false -> none
+ end.
+
+loop(LastNow, Size, Unit) ->
+ receive
+ {stamp, Msg, Now} ->
+ io:format(" ~-10s (+~4.2fs):", [Msg, diff(Now, LastNow)]),
+ loop(Now, 0, "");
+ {stamp, Now} ->
+ SizeStr =
+ case Size of
+ 0 -> "";
+ _ ->
+ Data = io_lib:format("~p ~s",[Size, Unit]),
+ io_lib:format(" (~12s)",[Data])
+ end,
+ io:format("~7.2fs~s\n", [diff(Now, LastNow), SizeStr]),
+ loop(Now, 0, "");
+ {size, NewSize, NewUnit} ->
+ loop(LastNow, NewSize, NewUnit);
+ {Pid, stop, Now} ->
+ io:format(" ~-9s (+~5.2fs)\n", ["",diff(Now, LastNow)]),
+ Pid ! ok;
+ {Pid, stop} ->
+ Pid ! ok
+ end.
+
+debug_loop(Phase) ->
+ receive
+ Message ->
+ {Runtime,_} = statistics(wall_clock),
+ Procs = erlang:system_info(process_count),
+ ProcMem = erlang:memory(total),
+ Status = io_lib:format("~12w ~6w ~20w", [Runtime, Procs, ProcMem]),
+ case Message of
+ {stamp, Msg, _Now} ->
+ io:format("~s ~s_start\n", [Status, Msg]),
+ debug_loop(Msg);
+ {stamp, _Now} ->
+ io:format("~s ~s_stop\n", [Status, Phase]),
+ debug_loop("");
+ {Pid, stop, _Now} ->
+ Pid ! ok;
+ {Pid, stop} ->
+ Pid ! ok;
+ _ ->
+ debug_loop(Phase)
+ end
+ after
+ 50 ->
+ {Runtime,_} = statistics(wall_clock),
+ Procs = erlang:system_info(process_count),
+ ProcMem = erlang:memory(total),
+ Status = io_lib:format("~12w ~6w ~20w", [Runtime, Procs, ProcMem]),
+ io:format("~s\n", [Status]),
+ debug_loop(Phase)
+ end.
+
+
+-spec start_stamp(timing_server(), string()) -> ok.
+
+start_stamp(none, _) -> ok;
+start_stamp(Pid, Msg) ->
+ Pid ! {stamp, Msg, now()},
+ ok.
+
+-spec end_stamp(timing_server()) -> ok.
+
+end_stamp(none) -> ok;
+end_stamp(Pid) ->
+ Pid ! {stamp, now()},
+ ok.
+
+-spec send_size_info(timing_server(), integer(), string()) -> ok.
+
+send_size_info(none, _, _) -> ok;
+send_size_info(Pid, Size, Unit) ->
+ Pid ! {size, Size, Unit},
+ ok.
+
+-spec stop(timing_server()) -> ok.
+
+stop(none) -> ok;
+stop(Pid) ->
+ Pid ! {self(), stop, now()},
+ receive ok -> ok end.
+
+diff(T2, T1) ->
+ timer:now_diff(T2,T1) / 1000000.
diff --git a/lib/dialyzer/src/dialyzer_typesig.erl b/lib/dialyzer/src/dialyzer_typesig.erl
index d0d27740f3..e997eedf76 100644
--- a/lib/dialyzer/src/dialyzer_typesig.erl
+++ b/lib/dialyzer/src/dialyzer_typesig.erl
@@ -91,23 +91,25 @@
-type typesig_scc() :: [{mfa(), {cerl:c_var(), cerl:c_fun()}, dict()}].
-type typesig_funmap() :: [{type_var(), type_var()}]. %% Orddict
--record(state, {callgraph :: dialyzer_callgraph:callgraph(),
- cs = [] :: [constr()],
- cmap = dict:new() :: dict(),
- fun_map = [] :: typesig_funmap(),
- fun_arities = dict:new() :: dict(),
- in_match = false :: boolean(),
- in_guard = false :: boolean(),
- module :: module(),
- name_map = dict:new() :: dict(),
- next_label :: label(),
- self_recs :: [label()],
- plt :: dialyzer_plt:plt(),
- prop_types = dict:new() :: dict(),
- records = dict:new() :: dict(),
- opaques = [] :: [erl_types:erl_type()],
- scc = [] :: [type_var()],
- mfas = [] :: [dialyzer_callgraph:mfa_or_funlbl()]
+-type dict_or_ets() :: {'d', dict()} | {'e', ets:tid()}.
+
+-record(state, {callgraph :: dialyzer_callgraph:callgraph(),
+ cs = [] :: [constr()],
+ cmap = {'d', dict:new()} :: dict_or_ets(),
+ fun_map = [] :: typesig_funmap(),
+ fun_arities = dict:new() :: dict(),
+ in_match = false :: boolean(),
+ in_guard = false :: boolean(),
+ module :: module(),
+ name_map = dict:new() :: dict(),
+ next_label = 0 :: label(),
+ self_rec :: erl_types:erl_type(),
+ plt :: dialyzer_plt:plt(),
+ prop_types = {'d', dict:new()} :: dict_or_ets(),
+ records = dict:new() :: dict(),
+ opaques = [] :: [erl_types:erl_type()],
+ scc = [] :: [type_var()],
+ mfas :: [tuple()]
}).
%%-----------------------------------------------------------------------------
@@ -1665,7 +1667,12 @@ solve([Fun], State) ->
solve([_|_] = SCC, State) ->
?debug("============ Analyzing SCC: ~w ===========\n",
[[debug_lookup_name(F) || F <- SCC]]),
- solve_scc(SCC, dict:new(), State, false).
+ {Parallel, NewState} =
+ case parallel_split(SCC) of
+ false -> {false, State};
+ SplitSCC -> {SplitSCC, minimize_state(State)}
+ end,
+ solve_scc(SCC, Parallel, dict:new(), NewState, false).
solve_fun(Fun, FunMap, State) ->
Cs = state__get_cs(Fun, State),
@@ -1680,8 +1687,7 @@ solve_fun(Fun, FunMap, State) ->
end,
enter_type(Fun, NewType, NewFunMap1).
-solve_scc(SCC, Map, State, TryingUnit) ->
- State1 = state__mark_as_non_self_rec(SCC, State),
+solve_scc(SCC, Parallel, Map, State, TryingUnit) ->
Vars0 = [{Fun, state__get_rec_var(Fun, State)} || Fun <- SCC],
Vars = [Var || {_, {ok, Var}} <- Vars0],
Funs = [Fun || {Fun, {ok, _}} <- Vars0],
@@ -1692,9 +1698,12 @@ solve_scc(SCC, Map, State, TryingUnit) ->
end, Map, SCC),
Map1 = enter_type_lists(Vars, RecTypes, CleanMap),
?debug("Checking SCC: ~w\n", [[debug_lookup_name(F) || F <- SCC]]),
- SolveFun = fun(X, Y) -> scc_fold_fun(X, Y, State1) end,
- Map2 = lists:foldl(SolveFun, Map1, SCC),
FunSet = ordsets:from_list([t_var_name(F) || F <- SCC]),
+ Map2 =
+ case Parallel of
+ false -> solve_whole_scc(SCC, Map1, State);
+ SplitSCC -> solve_whole_scc_parallel(SplitSCC, Map1, State)
+ end,
case maps_are_equal(Map2, Map, FunSet) of
true ->
?debug("SCC ~w reached fixpoint\n", [SCC]),
@@ -1708,15 +1717,127 @@ solve_scc(SCC, Map, State, TryingUnit) ->
true -> t_fun(t_fun_args(T), t_unit())
end || T <- NewTypes],
Map3 = enter_type_lists(Funs, UnitTypes, Map2),
- solve_scc(SCC, Map3, State, true);
+ solve_scc(SCC, Parallel, Map3, State, true);
false ->
+ case Parallel of
+ false -> true;
+ _ -> dispose_state(State)
+ end,
Map2
end;
false ->
?debug("SCC ~w did not reach fixpoint\n", [SCC]),
- solve_scc(SCC, Map2, State, TryingUnit)
+ solve_scc(SCC, Parallel, Map2, State, TryingUnit)
+ end.
+
+solve_whole_scc(SCC, Map, State) ->
+ SolveFun = fun(X, Y) -> scc_fold_fun(X, Y, State) end,
+ lists:foldl(SolveFun, Map, SCC).
+
+%%------------------------------------------------------------------------------
+
+-define(worth_it, 42).
+
+parallel_split(SCC) ->
+ Length = length(SCC),
+ case Length > 2*?worth_it of
+ false -> false;
+ true ->
+ case min(dialyzer_utils:parallelism(), 8) of
+ 1 -> false;
+ CPUs ->
+ FullShare = Length div CPUs + 1,
+ Unit = max(FullShare, ?worth_it),
+ split(SCC, Unit, [])
+ end
+ end.
+
+minimize_state(#state{
+ cmap = {d, CMap},
+ fun_map = FunMap,
+ fun_arities = FunArities,
+ self_rec = SelfRec,
+ prop_types = {d, PropTypes},
+ opaques = Opaques
+ }) ->
+ ETSCMap = ets:new(cmap,[{read_concurrency, true}]),
+ ETSPropTypes = ets:new(prop_types,[{read_concurrency, true}]),
+ true = ets:insert(ETSCMap, dict:to_list(CMap)),
+ true = ets:insert(ETSPropTypes, dict:to_list(PropTypes)),
+ #state
+ {cmap = {e, ETSCMap},
+ fun_map = FunMap,
+ fun_arities = FunArities,
+ self_rec = SelfRec,
+ prop_types = {e, ETSPropTypes},
+ opaques = Opaques
+ }.
+
+dispose_state(#state{cmap = {e, ETSCMap},
+ prop_types = {e, ETSPropTypes}}) ->
+ true = ets:delete(ETSCMap),
+ true = ets:delete(ETSPropTypes).
+
+solve_whole_scc_parallel(SplitSCC, Map, State) ->
+ Workers = spawn_workers(SplitSCC, Map, State),
+ wait_results(Workers, Map, fold_res_fun(State)).
+
+spawn_workers(SplitSCC, Map, State) ->
+ Spawner = solve_scc_spawner(self(), Map, State),
+ lists:foreach(Spawner, SplitSCC),
+ length(SplitSCC).
+
+wait_results(0, Map, _FoldResFun) ->
+ Map;
+wait_results(Pending, Map, FoldResFun) ->
+ Res = receive_scc_result(),
+ NewMap = lists:foldl(FoldResFun, Map, Res),
+ wait_results(Pending-1, NewMap, FoldResFun).
+
+solve_scc_spawner(Parent, Map, State) ->
+ fun(SCCPart) ->
+ spawn_link(fun() -> solve_scc_worker(Parent, SCCPart, Map, State) end)
+ end.
+
+split([], _Unit, Acc) ->
+ Acc;
+split(List, Unit, Acc) ->
+ {Taken, Rest} =
+ try
+ lists:split(Unit, List)
+ catch
+ _:_ -> {List, []}
+ end,
+ split(Rest, Unit, [Taken|Acc]).
+
+solve_scc_worker(Parent, SCCPart, Map, State) ->
+ SolveFun = fun(X, Y) -> scc_fold_fun(X, Y, State) end,
+ FinalMap = lists:foldl(SolveFun, Map, SCCPart),
+ Res =
+ [{F, t_limit(unsafe_lookup_type(F, FinalMap), ?TYPE_LIMIT)} ||
+ F <- SCCPart],
+ send_scc_result(Parent, Res).
+
+fold_res_fun(State) ->
+ fun({F, Type}, Map) ->
+ case state__get_rec_var(F, State) of
+ {ok, R} ->
+ enter_type(R, Type, enter_type(F, Type, Map));
+ error ->
+ enter_type(F, Type, Map)
+ end
end.
+receive_scc_result() ->
+ receive
+ {scc_fun, Res} -> Res
+ end.
+
+send_scc_result(Parent, Res) ->
+ Parent ! {scc_fun, Res}.
+
+%%------------------------------------------------------------------------------
+
scc_fold_fun(F, FunMap, State) ->
Deps = get_deps(state__get_cs(F, State)),
Cs = mk_constraint_ref(F, Deps),
@@ -1787,13 +1908,17 @@ solve_ref_or_list(#constraint_list{type=Type, list = Cs, deps = Deps, id = Id},
{ok, M} -> {M, true}
end,
?debug("Checking ref to list: ~w\n", [Id]),
- case Check andalso maps_are_equal(OldLocalMap, Map, Deps) of
+ if
+ OldLocalMap =:= error -> {error, MapDict};
true ->
- ?debug("~w equal ~w\n", [Type, Id]),
- {ok, MapDict, Map};
- false ->
- ?debug("~w not equal: ~w. Solving\n", [Type, Id]),
- solve_clist(Cs, Type, Id, Deps, MapDict, Map, State)
+ case Check andalso maps_are_equal(OldLocalMap, Map, Deps) of
+ true ->
+ ?debug("~w equal ~w\n", [Type, Id]),
+ {ok, MapDict, Map};
+ false ->
+ ?debug("~w not equal: ~w. Solving\n", [Type, Id]),
+ solve_clist(Cs, Type, Id, Deps, MapDict, Map, State)
+ end
end.
solve_self_recursive(Cs, Map, MapDict, Id, RecType0, State) ->
@@ -1802,7 +1927,7 @@ solve_self_recursive(Cs, Map, MapDict, Id, RecType0, State) ->
?debug("OldRecType ~s\n", [format_type(RecType0)]),
RecType = t_limit(RecType0, ?TYPE_LIMIT),
Map1 = enter_type(RecVar, RecType, dict:erase(t_var_name(Id), Map)),
- ?debug("\tMap in: ~p\n",[[{X, format_type(Y)}||{X, Y}<-dict:to_list(Map1)]]),
+ pp_map("Map1", Map1),
case solve_ref_or_list(Cs, Map1, MapDict, State) of
{error, _} = Error ->
case t_is_none(RecType0) of
@@ -1815,8 +1940,7 @@ solve_self_recursive(Cs, Map, MapDict, Id, RecType0, State) ->
Error
end;
{ok, NewMapDict, NewMap} ->
- ?debug("\tMap: ~p\n",
- [[{X, format_type(Y)} || {X, Y} <- dict:to_list(NewMap)]]),
+ pp_map("NewMap", NewMap),
NewRecType = unsafe_lookup_type(Id, NewMap),
case t_is_equal(NewRecType, RecType0) of
true ->
@@ -1828,7 +1952,8 @@ solve_self_recursive(Cs, Map, MapDict, Id, RecType0, State) ->
solve_clist(Cs, conj, Id, Deps, MapDict, Map, State) ->
case solve_cs(Cs, Map, MapDict, State) of
- {error, _} = Error -> Error;
+ {error, NewMapDict} ->
+ {error, dict:store(Id, error, NewMapDict)};
{ok, NewMapDict, NewMap} = Ret ->
case Cs of
[_] ->
@@ -1850,7 +1975,7 @@ solve_clist(Cs, disj, Id, _Deps, MapDict, Map, State) ->
end,
{Maps, NewMapDict} = lists:mapfoldl(Fun, MapDict, Cs),
case [X || {ok, X} <- Maps] of
- [] -> {error, NewMapDict};
+ [] -> {error, dict:store(Id, error, NewMapDict)};
MapList ->
NewMap = join_maps(MapList),
{ok, dict:store(Id, NewMap, NewMapDict), NewMap}
@@ -1926,6 +2051,8 @@ solve_subtype(Type, Inf, Map, Opaques) ->
%%
%% ============================================================================
+join_maps([Map]) ->
+ Map;
join_maps(Maps) ->
Keys = lists:foldl(fun(TmpMap, AccKeys) ->
[Key || Key <- AccKeys, dict:is_key(Key, TmpMap)]
@@ -2079,6 +2206,12 @@ mk_var_no_lit(Var) ->
mk_var_no_lit_list(List) ->
[mk_var_no_lit(X) || X <- List].
+pp_map(_S, _Map) ->
+ ?debug("\t~s: ~p\n",
+ [_S, [{X, lists:flatten(format_type(Y))} ||
+ {X, Y} <- lists:keysort(1, dict:to_list(_Map))]]).
+
+
%% ============================================================================
%%
%% The State.
@@ -2090,11 +2223,19 @@ new_state(SCC0, NextLabel, CallGraph, Plt, PropTypes) ->
NameMap = dict:from_list(List),
MFAs = [MFA || {MFA, _Var} <- List],
SCC = [mk_var(Fun) || {_MFA, {_Var, Fun}, _Rec} <- SCC0],
- SelfRecs = [F || F <- SCC,
- dialyzer_callgraph:is_self_rec(t_var_name(F), CallGraph)],
+ SelfRec =
+ case SCC of
+ [OneF] ->
+ Label = t_var_name(OneF),
+ case dialyzer_callgraph:is_self_rec(Label, CallGraph) of
+ true -> OneF;
+ false -> false
+ end;
+ _Many -> false
+ end,
#state{callgraph = CallGraph, name_map = NameMap, next_label = NextLabel,
- prop_types = PropTypes, plt = Plt, scc = ordsets:from_list(SCC),
- mfas = MFAs, self_recs = ordsets:from_list(SelfRecs)}.
+ prop_types = {d, PropTypes}, plt = Plt, scc = ordsets:from_list(SCC),
+ mfas = MFAs, self_rec = SelfRec}.
state__set_rec_dict(State, RecDict) ->
State#state{records = RecDict}.
@@ -2193,14 +2334,21 @@ state__plt(#state{plt = PLT}) ->
state__new_constraint_context(State) ->
State#state{cs = []}.
-state__prop_domain(FunLabel, #state{prop_types = PropTypes}) ->
+state__prop_domain(FunLabel, #state{prop_types = {e, ETSPropTypes}}) ->
+ try ets:lookup_element(ETSPropTypes, FunLabel, 2) of
+ {_Range_Fun, Dom} -> {ok, Dom};
+ FunType -> {ok, t_fun_args(FunType)}
+ catch
+ _:_ -> error
+ end;
+state__prop_domain(FunLabel, #state{prop_types = {d, PropTypes}}) ->
case dict:find(FunLabel, PropTypes) of
error -> error;
{ok, {_Range_Fun, Dom}} -> {ok, Dom};
{ok, FunType} -> {ok, t_fun_args(FunType)}
end.
-state__add_prop_constrs(Tree, #state{prop_types = PropTypes} = State) ->
+state__add_prop_constrs(Tree, #state{prop_types = {d, PropTypes}} = State) ->
Label = cerl_trees:get_label(Tree),
case dict:find(Label, PropTypes) of
error -> State;
@@ -2263,21 +2411,17 @@ state__mk_vars(N, #state{next_label = NL} = State) ->
Vars = [t_var(X) || X <- lists:seq(NL, NewLabel-1)],
{State#state{next_label = NewLabel}, Vars}.
-state__store_constrs(Id, Cs, #state{cmap = Dict} = State) ->
+state__store_constrs(Id, Cs, #state{cmap = {d, Dict}} = State) ->
NewDict = dict:store(Id, Cs, Dict),
- State#state{cmap = NewDict}.
+ State#state{cmap = {d, NewDict}}.
-state__get_cs(Var, #state{cmap = Dict}) ->
+state__get_cs(Var, #state{cmap = {e, ETSDict}}) ->
+ ets:lookup_element(ETSDict, Var, 2);
+state__get_cs(Var, #state{cmap = {d, Dict}}) ->
dict:fetch(Var, Dict).
-%% The functions here will not be treated as self recursive.
-%% These functions will need to be handled as such manually.
-state__mark_as_non_self_rec(SCC, #state{self_recs = SelfRecs} = State) ->
- %% TODO: Check if the result is always empty and just set it to [] if so.
- State#state{self_recs = ordsets:subtract(SelfRecs, ordsets:from_list(SCC))}.
-
-state__is_self_rec(Fun, #state{self_recs = SelfRecs}) ->
- ordsets:is_element(Fun, SelfRecs).
+state__is_self_rec(Fun, #state{self_rec = SelfRec}) ->
+ Fun =:= SelfRec.
state__store_funs(Vars0, Funs0, #state{fun_map = Map} = State) ->
debug_make_name_map(Vars0, Funs0),
@@ -2523,19 +2667,21 @@ enumerate_constraints([#constraint_ref{id = Id} = C|Tail], N, Acc, State) ->
enumerate_constraints([#constraint_list{type = conj, list = List} = C|Tail],
N, Acc, State) ->
%% Separate the flat constraints from the deep ones to make a
- %% separate fixpoint interation over the flat ones for speed.
- {Flat, Deep} = lists:splitwith(fun(#constraint{}) -> true;
+ %% separate fixpoint iteration over the flat ones for speed.
+ {Flat, Deep} = lists:partition(fun(#constraint{}) -> true;
(#constraint_list{}) -> false;
(#constraint_ref{}) -> false
end, List),
{NewFlat, N1, State1} = enumerate_constraints(Flat, N, [], State),
{NewDeep, N2, State2} = enumerate_constraints(Deep, N1, [], State1),
{NewList, N3} =
- case shorter_than_two(NewFlat) orelse (NewDeep =:= []) of
- true -> {NewFlat ++ NewDeep, N2};
- false ->
- {NewCLists, TmpN} = group_constraints_in_components(NewFlat, N2),
- {NewCLists ++ NewDeep, TmpN}
+ if
+ NewFlat =:= [] -> {NewDeep, N2};
+ NewDeep =:= [] -> {NewFlat, N2};
+ true ->
+ TmpCList = mk_conj_constraint_list(NewFlat),
+ {[TmpCList#constraint_list{id = {list, N2}} | NewDeep],
+ N2 + 1}
end,
NewAcc = [C#constraint_list{list = NewList, id = {list, N3}}|Acc],
enumerate_constraints(Tail, N3+1, NewAcc, State2);
@@ -2549,42 +2695,6 @@ enumerate_constraints([#constraint{} = C|Tail], N, Acc, State) ->
enumerate_constraints([], N, Acc, State) ->
{lists:reverse(Acc), N, State}.
-shorter_than_two([]) -> true;
-shorter_than_two([_]) -> true;
-shorter_than_two([_|_]) -> false.
-
-group_constraints_in_components(Cs, N) ->
- DepList = [Deps || #constraint{deps = Deps} <- Cs],
- case find_dep_components(DepList, []) of
- [_] -> {Cs, N};
- [_|_] = Components ->
- ConstrComp = [[C || #constraint{deps = D} = C <- Cs,
- ordsets:is_subset(D, Comp)]
- || Comp <- Components],
- lists:mapfoldl(fun(CComp, TmpN) ->
- TmpCList = mk_conj_constraint_list(CComp),
- {TmpCList#constraint_list{id = {list, TmpN}},
- TmpN + 1}
- end, N, ConstrComp)
- end.
-
-find_dep_components([Set|Left], AccComponents) ->
- {Component, Ungrouped} = find_dep_components(Left, Set, []),
- case Component =:= Set of
- true -> find_dep_components(Ungrouped, [Component|AccComponents]);
- false -> find_dep_components([Component|Ungrouped], AccComponents)
- end;
-find_dep_components([], AccComponents) ->
- AccComponents.
-
-find_dep_components([Set|Left], AccSet, Ungrouped) ->
- case ordsets:intersection(Set, AccSet) of
- [] -> find_dep_components(Left, AccSet, [Set|Ungrouped]);
- [_|_] -> find_dep_components(Left, ordsets:union(Set, AccSet), Ungrouped)
- end;
-find_dep_components([], AccSet, Ungrouped) ->
- {AccSet, Ungrouped}.
-
%% Put the fun ref constraints last in any conjunction since we need
%% to separate the environment from the interior of the function.
order_fun_constraints(State) ->
@@ -2714,13 +2824,24 @@ lookup_record(Records, Tag, Arity) ->
-ifdef(DEBUG).
format_type(#fun_var{deps = Deps, origin = Origin}) ->
- io_lib:format("Fun@L~p(~s)",
- [Origin, lists:flatten([format_type(t_var(X))||X<-Deps])]);
+ L = [format_type(t_var(X)) || X <- Deps],
+ io_lib:format("Fun@L~p(~s)", [Origin, join_chars(L, ",")]);
format_type(Type) ->
case cerl:is_literal(Type) of
true -> io_lib:format("~w", [cerl:concrete(Type)]);
false -> erl_types:t_to_string(Type)
end.
+
+join_chars([], _Sep) ->
+ [];
+join_chars([H | T], Sep) ->
+ [H | [[Sep,X] || X <- T]].
+
+debug_lookup_name(Var) ->
+ case dict:find(t_var_name(Var), get(dialyzer_typesig_map)) of
+ error -> Var;
+ {ok, Name} -> Name
+ end.
-endif.
-ifdef(DEBUG_NAME_MAP).
@@ -2739,12 +2860,6 @@ debug_make_name_map([Var|VarLeft], [Fun|FunLeft], Map) ->
debug_make_name_map([], [], Map) ->
Map.
-debug_lookup_name(Var) ->
- case dict:find(t_var_name(Var), get(dialyzer_typesig_map)) of
- error -> Var;
- {ok, Name} -> Name
- end.
-
-else.
debug_make_name_map(_Vars, _Funs) ->
ok.
@@ -2755,51 +2870,55 @@ pp_constrs_scc(SCC, State) ->
[pp_constrs(Fun, state__get_cs(Fun, State), State) || Fun <- SCC].
pp_constrs(Fun, Cs, State) ->
- io:format("Constraints for fun: ~w\n", [debug_lookup_name(Fun)]),
+ io:format("Constraints for fun: ~w", [debug_lookup_name(Fun)]),
MaxDepth = pp_constraints(Cs, State),
io:format("Depth: ~w\n", [MaxDepth]).
pp_constraints(Cs, State) ->
- Res = pp_constraints([Cs], none, 0, 0, State),
+ Res = pp_constraints([Cs], 0, 0, State),
io:nl(),
Res.
-pp_constraints([List|Tail], Separator, Level, MaxDepth,
- State) when is_list(List) ->
- pp_constraints(List++Tail, Separator, Level, MaxDepth, State);
-pp_constraints([#constraint_ref{id = Id}|Left], Separator,
- Level, MaxDepth, State) ->
+pp_constraints([List|Tail], Level, MaxDepth, State) when is_list(List) ->
+ pp_constraints(List++Tail, Level, MaxDepth, State);
+pp_constraints([#constraint_ref{id = Id}|Left], Level, MaxDepth, State) ->
Cs = state__get_cs(Id, State),
+ pp_indent(Level),
io:format("%Ref ~w%", [t_var_name(Id)]),
- pp_constraints([Cs|Left], Separator, Level, MaxDepth, State);
-pp_constraints([#constraint{lhs = Lhs, op = Op, rhs = Rhs}], _Separator,
- Level, MaxDepth, _State) ->
- io:format("~s ~w ~s", [format_type(Lhs), Op, format_type(Rhs)]),
+ pp_constraints([Cs|Left], Level, MaxDepth, State);
+pp_constraints([#constraint{}=C], Level, MaxDepth, _State) ->
+ pp_op(C, Level),
erlang:max(Level, MaxDepth);
-pp_constraints([#constraint{lhs = Lhs, op = Op, rhs = Rhs}|Tail], Separator,
- Level, MaxDepth, State) ->
- io:format("~s ~w ~s ~s ", [format_type(Lhs), Op, format_type(Rhs),Separator]),
- pp_constraints(Tail, Separator, Level, MaxDepth, State);
+pp_constraints([#constraint{}=C|Tail], Level, MaxDepth, State) ->
+ pp_op(C, Level),
+ pp_constraints(Tail, Level, MaxDepth, State);
pp_constraints([#constraint_list{type = Type, list = List, id = Id}],
- _Separator, Level, MaxDepth, State) ->
- io:format("%List ~w(", [Id]),
- NewSeparator = case Type of
- conj -> "*";
- disj -> "+"
- end,
- NewMaxDepth = pp_constraints(List, NewSeparator, Level + 1, MaxDepth, State),
+ Level, MaxDepth, State) ->
+ pp_indent(Level),
+ case Type of
+ conj -> io:format("Conj ~w (", [Id]);
+ disj -> io:format("Disj ~w (", [Id])
+ end,
+ NewMaxDepth = pp_constraints(List, Level + 1, MaxDepth, State),
io:format(")", []),
NewMaxDepth;
pp_constraints([#constraint_list{type = Type, list = List, id = Id}|Tail],
- Separator, Level, MaxDepth, State) ->
- io:format("List ~w(", [Id]),
- NewSeparator = case Type of
- conj -> "*";
- disj -> "+"
- end,
- NewMaxDepth = pp_constraints(List, NewSeparator, Level+1, MaxDepth, State),
- io:format(") ~s\n~s ", [Separator, Separator]),
- pp_constraints(Tail, Separator, Level, NewMaxDepth, State).
+ Level, MaxDepth, State) ->
+ pp_indent(Level),
+ case Type of
+ conj -> io:format("Conj ~w (", [Id]);
+ disj -> io:format("Disj ~w (", [Id])
+ end,
+ NewMaxDepth = pp_constraints(List, Level+1, MaxDepth, State),
+ io:format(")", []),
+ pp_constraints(Tail, Level, NewMaxDepth, State).
+
+pp_op(#constraint{lhs = Lhs, op = Op, rhs = Rhs}, Level) ->
+ pp_indent(Level),
+ io:format("~s ~w ~s", [format_type(Lhs), Op, format_type(Rhs)]).
+
+pp_indent(Level) ->
+ io:format("\n~*s", [Level*2, ""]).
-else.
pp_constrs_scc(_SCC, _State) ->
ok.
diff --git a/lib/dialyzer/src/dialyzer_utils.erl b/lib/dialyzer/src/dialyzer_utils.erl
index 2a248fb028..149e777e1f 100644
--- a/lib/dialyzer/src/dialyzer_utils.erl
+++ b/lib/dialyzer/src/dialyzer_utils.erl
@@ -43,7 +43,8 @@
pp_hook/0,
process_record_remote_types/1,
sets_filter/2,
- src_compiler_opts/0
+ src_compiler_opts/0,
+ parallelism/0
]).
-include("dialyzer.hrl").
@@ -536,3 +537,12 @@ pp_unit(Unit, Ctxt, Cont) ->
pp_atom(Atom) ->
String = atom_to_list(cerl:atom_val(Atom)),
prettypr:text(String).
+
+%%------------------------------------------------------------------------------
+
+-spec parallelism() -> integer().
+
+parallelism() ->
+ CPUs = erlang:system_info(logical_processors_available),
+ Schedulers = erlang:system_info(schedulers),
+ min(CPUs, Schedulers).
diff --git a/lib/dialyzer/src/dialyzer_worker.erl b/lib/dialyzer/src/dialyzer_worker.erl
new file mode 100644
index 0000000000..50b2e31ed8
--- /dev/null
+++ b/lib/dialyzer/src/dialyzer_worker.erl
@@ -0,0 +1,189 @@
+%% -*- erlang-indent-level: 2 -*-
+%%-----------------------------------------------------------------------
+%% %CopyrightBegin%
+%%
+%% Copyright Ericsson AB 2006-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
+%% compliance with the License. You should have received a copy of the
+%% Erlang Public License along with this software. If not, it can be
+%% retrieved online at http://www.erlang.org/.
+%%
+%% Software distributed under the License is distributed on an "AS IS"
+%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+%% the License for the specific language governing rights and limitations
+%% under the License.
+%%
+%% %CopyrightEnd%
+%%
+
+-module(dialyzer_worker).
+
+-export([launch/4, sequential/4]).
+
+-export_type([worker/0]).
+
+-type worker() :: pid(). %%opaque
+
+-type mode() :: dialyzer_coordinator:mode().
+-type coordinator() :: dialyzer_coordinator:coordinator().
+-type init_data() :: dialyzer_coordinator:init_data().
+-type result() :: dialyzer_coordinator:result().
+
+-record(state, {
+ mode :: mode(),
+ job :: mfa_or_funlbl() | file:filename(),
+ coordinator :: coordinator(),
+ init_data :: init_data(),
+ depends_on = [] :: list()
+ }).
+
+-include("dialyzer.hrl").
+
+%% -define(DEBUG, true).
+
+-ifdef(DEBUG).
+-define(debug(X__, Y__), io:format(X__, Y__)).
+-else.
+-define(debug(X__, Y__), ok).
+-endif.
+
+%%--------------------------------------------------------------------
+
+-spec launch(mode(), [mfa_or_funlbl()], init_data(), coordinator()) -> worker().
+
+launch(Mode, Job, InitData, Coordinator) ->
+ State = #state{mode = Mode,
+ job = Job,
+ init_data = InitData,
+ coordinator = Coordinator},
+ InitState =
+ case Mode of
+ X when X =:= 'typesig'; X =:= 'dataflow' -> initializing;
+ X when X =:= 'compile'; X =:= 'warnings' -> running
+ end,
+ spawn_link(fun() -> loop(InitState, State) end).
+
+%%--------------------------------------------------------------------
+
+loop(updating, State) ->
+ ?debug("Update: ~p\n",[State#state.job]),
+ NextStatus =
+ case waits_more_success_typings(State) of
+ true -> waiting;
+ false -> running
+ end,
+ loop(NextStatus, State);
+loop(initializing, #state{job = SCC, init_data = InitData} = State) ->
+ DependsOn = dialyzer_succ_typings:find_depends_on(SCC, InitData),
+ ?debug("Deps ~p: ~p\n",[State#state.job, DependsOn]),
+ loop(updating, State#state{depends_on = DependsOn});
+loop(waiting, State) ->
+ ?debug("Wait: ~p\n",[State#state.job]),
+ NewState = wait_for_success_typings(State),
+ loop(updating, NewState);
+loop(running, #state{mode = 'compile'} = State) ->
+ dialyzer_coordinator:wait_activation(),
+ ?debug("Compile: ~s\n",[State#state.job]),
+ Result =
+ case start_compilation(State) of
+ {ok, EstimatedSize, Data} ->
+ Label = ask_coordinator_for_label(EstimatedSize, State),
+ continue_compilation(Label, Data);
+ {error, _Reason} = Error ->
+ Error
+ end,
+ report_to_coordinator(Result, State);
+loop(running, #state{mode = 'warnings'} = State) ->
+ dialyzer_coordinator:wait_activation(),
+ ?debug("Warning: ~s\n",[State#state.job]),
+ Result = collect_warnings(State),
+ report_to_coordinator(Result, State);
+loop(running, #state{mode = Mode} = State) when
+ Mode =:= 'typesig'; Mode =:= 'dataflow' ->
+ request_activation(State),
+ ?debug("Run: ~p\n",[State#state.job]),
+ NotFixpoint = do_work(State),
+ ok = broadcast_done(State),
+ report_to_coordinator(NotFixpoint, State).
+
+waits_more_success_typings(#state{depends_on = Depends}) ->
+ Depends =/= [].
+
+broadcast_done(#state{job = SCC, init_data = InitData,
+ coordinator = Coordinator}) ->
+ RequiredBy = dialyzer_succ_typings:find_required_by(SCC, InitData),
+ {Callers, Unknown} =
+ dialyzer_coordinator:sccs_to_pids(RequiredBy, Coordinator),
+ send_done(Callers, SCC),
+ continue_broadcast_done(Unknown, SCC, Coordinator).
+
+send_done(Callers, SCC) ->
+ ?debug("Sending ~p: ~p\n",[SCC, Callers]),
+ SendSTFun = fun(PID) -> PID ! {done, SCC} end,
+ lists:foreach(SendSTFun, Callers).
+
+continue_broadcast_done([], _SCC, _Coordinator) -> ok;
+continue_broadcast_done(Rest, SCC, Coordinator) ->
+ %% This time limit should be greater than the time required
+ %% by the coordinator to spawn all processes.
+ timer:sleep(500),
+ {Callers, Unknown} = dialyzer_coordinator:sccs_to_pids(Rest, Coordinator),
+ send_done(Callers, SCC),
+ continue_broadcast_done(Unknown, SCC, Coordinator).
+
+wait_for_success_typings(#state{depends_on = DependsOn} = State) ->
+ receive
+ {done, SCC} ->
+ ?debug("GOT ~p: ~p\n",[State#state.job, SCC]),
+ State#state{depends_on = DependsOn -- [SCC]}
+ after
+ 5000 ->
+ ?debug("Still Waiting ~p: ~p\n",[State#state.job, DependsOn]),
+ State
+ end.
+
+request_activation(#state{coordinator = Coordinator}) ->
+ dialyzer_coordinator:request_activation(Coordinator).
+
+do_work(#state{mode = Mode, job = Job, init_data = InitData}) ->
+ case Mode of
+ typesig -> dialyzer_succ_typings:find_succ_types_for_scc(Job, InitData);
+ dataflow -> dialyzer_succ_typings:refine_one_module(Job, InitData)
+ end.
+
+report_to_coordinator(Result, #state{job = Job, coordinator = Coordinator}) ->
+ ?debug("Done: ~p\n",[Job]),
+ dialyzer_coordinator:job_done(Job, Result, Coordinator).
+
+start_compilation(#state{job = Job, init_data = InitData}) ->
+ dialyzer_analysis_callgraph:start_compilation(Job, InitData).
+
+ask_coordinator_for_label(EstimatedSize, #state{coordinator = Coordinator}) ->
+ dialyzer_coordinator:get_next_label(EstimatedSize, Coordinator).
+
+continue_compilation(Label, Data) ->
+ dialyzer_analysis_callgraph:continue_compilation(Label, Data).
+
+collect_warnings(#state{job = Job, init_data = InitData}) ->
+ dialyzer_succ_typings:collect_warnings(Job, InitData).
+
+%%------------------------------------------------------------------------------
+
+-type extra() :: label() | 'unused'.
+
+-spec sequential(mode(), [mfa_or_funlbl()], init_data(), extra()) -> result().
+
+sequential('compile', Job, InitData, Extra) ->
+ case dialyzer_analysis_callgraph:start_compilation(Job, InitData) of
+ {ok, EstimatedSize, Data} ->
+ {EstimatedSize, continue_compilation(Extra, Data)};
+ {error, _Reason} = Error -> {0, Error}
+ end;
+sequential('typesig', Job, InitData, _Extra) ->
+ dialyzer_succ_typings:find_succ_types_for_scc(Job, InitData);
+sequential('dataflow', Job, InitData, _Extra) ->
+ dialyzer_succ_typings:refine_one_module(Job, InitData);
+sequential('warnings', Job, InitData, _Extra) ->
+ dialyzer_succ_typings:collect_warnings(Job, InitData).
diff --git a/lib/dialyzer/test/Makefile b/lib/dialyzer/test/Makefile
index 6a1abce943..9f8a3f1194 100644
--- a/lib/dialyzer/test/Makefile
+++ b/lib/dialyzer/test/Makefile
@@ -25,10 +25,10 @@ RELSYSDIR = $(RELEASE_PATH)/dialyzer_test
include $(ERL_TOP)/make/otp_release_targets.mk
release_tests_spec:
- $(INSTALL_DIR) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- $(INSTALL_DATA) $(AUXILIARY_FILES) $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- cd $(RELSYSDIR);\
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(AUXILIARY_FILES) "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ cd "$(RELSYSDIR)";\
erlc dialyzer_common.erl file_utils.erl;\
erl -noshell -run dialyzer_common create_all_suites -s erlang halt
diff --git a/lib/dialyzer/test/opaque_SUITE_data/results/queue b/lib/dialyzer/test/opaque_SUITE_data/results/queue
index 59ce33f098..c3f04ea64d 100644
--- a/lib/dialyzer/test/opaque_SUITE_data/results/queue
+++ b/lib/dialyzer/test/opaque_SUITE_data/results/queue
@@ -5,6 +5,7 @@ queue_use.erl:27: The attempt to match a term of type queue() against the patter
queue_use.erl:33: Attempt to test for equality between a term of type {[42,...],[]} and a term of opaque type queue()
queue_use.erl:36: The attempt to match a term of type queue() against the pattern {F, _R} breaks the opaqueness of the term
queue_use.erl:40: The call queue:out({[42,...],[]}) does not have an opaque term of type queue() as 1st argument
+queue_use.erl:48: The call queue_use:add_unique(42,#db{p::[],q::queue()}) contains an opaque term as 2nd argument when terms of different types are expected in these positions
queue_use.erl:51: The call queue_use:is_in_queue(E::42,DB::#db{p::[],q::queue()}) contains an opaque term as 2nd argument when terms of different types are expected in these positions
queue_use.erl:56: The attempt to match a term of type #db{p::[],q::queue()} against the pattern {'db', _, {L1, L2}} breaks the opaqueness of queue()
queue_use.erl:62: The call queue_use:tuple_queue({42,'gazonk'}) does not have a term of type {_,queue()} (with opaque subterms) as 1st argument
diff --git a/lib/dialyzer/test/small_SUITE_data/results/contracts_with_subtypes b/lib/dialyzer/test/small_SUITE_data/results/contracts_with_subtypes
new file mode 100644
index 0000000000..8dc0361b0d
--- /dev/null
+++ b/lib/dialyzer/test/small_SUITE_data/results/contracts_with_subtypes
@@ -0,0 +1,31 @@
+
+contracts_with_subtypes.erl:106: The call contracts_with_subtypes:rec_arg({'a','b'}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:107: The call contracts_with_subtypes:rec_arg({'b','a'}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:108: The call contracts_with_subtypes:rec_arg({'a',{'b','a'}}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:109: The call contracts_with_subtypes:rec_arg({'b',{'a','b'}}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:110: The call contracts_with_subtypes:rec_arg({'a',{'b',{'a','b'}}}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:111: The call contracts_with_subtypes:rec_arg({'b',{'a',{'b','a'}}}) breaks the contract (Arg) -> 'ok' when is_subtype(Arg,{'a',A} | {'b',B}), is_subtype(A,'a' | {'b',B}), is_subtype(B,'b' | {'a',A})
+contracts_with_subtypes.erl:142: The pattern 1 can never match the type binary() | string()
+contracts_with_subtypes.erl:145: The pattern 'alpha' can never match the type {'ok',X} | {'ok',X,binary() | string()}
+contracts_with_subtypes.erl:147: The pattern 42 can never match the type {'ok',_} | {'ok',_,binary() | string()}
+contracts_with_subtypes.erl:163: The pattern 'alpha' can never match the type {'ok',X}
+contracts_with_subtypes.erl:165: The pattern 42 can never match the type {'ok',X}
+contracts_with_subtypes.erl:183: The pattern 'alpha' can never match the type {'ok',X}
+contracts_with_subtypes.erl:185: The pattern 42 can never match the type {'ok',X}
+contracts_with_subtypes.erl:202: The pattern 1 can never match the type binary() | string()
+contracts_with_subtypes.erl:205: The pattern {'ok', _} can never match the type {'ok',X,binary() | string()}
+contracts_with_subtypes.erl:206: The pattern 'alpha' can never match the type {'ok',X,binary() | string()}
+contracts_with_subtypes.erl:207: The pattern {'ok', 42} can never match the type {'ok',X,binary() | string()}
+contracts_with_subtypes.erl:208: The pattern 42 can never match the type {'ok',X,binary() | string()}
+contracts_with_subtypes.erl:234: Function flat_ets_new_t/0 has no local return
+contracts_with_subtypes.erl:235: The call contracts_with_subtypes:flat_ets_new(12,[]) breaks the contract (Name,Options) -> atom() when is_subtype(Name,atom()), is_subtype(Options,[Option]), is_subtype(Option,'set' | 'ordered_set' | 'bag' | 'duplicate_bag' | 'public' | 'protected' | 'private' | 'named_table' | {'keypos',integer()} | {'heir',pid(),term()} | {'heir','none'} | {'write_concurrency',boolean()} | {'read_concurrency',boolean()} | 'compressed')
+contracts_with_subtypes.erl:23: Invalid type specification for function contracts_with_subtypes:extract2/0. The success typing is () -> 'something'
+contracts_with_subtypes.erl:261: Function factored_ets_new_t/0 has no local return
+contracts_with_subtypes.erl:262: The call contracts_with_subtypes:factored_ets_new(12,[]) breaks the contract (Name,Options) -> atom() when is_subtype(Name,atom()), is_subtype(Options,[Option]), is_subtype(Option,Type | Access | 'named_table' | {'keypos',Pos} | {'heir',Pid::pid(),HeirData} | {'heir','none'} | Tweaks), is_subtype(Type,type()), is_subtype(Access,access()), is_subtype(Tweaks,{'write_concurrency',boolean()} | {'read_concurrency',boolean()} | 'compressed'), is_subtype(Pos,pos_integer()), is_subtype(HeirData,term())
+contracts_with_subtypes.erl:77: The call contracts_with_subtypes:foo1(5) breaks the contract (Arg1) -> Res when is_subtype(Arg1,atom()), is_subtype(Res,atom())
+contracts_with_subtypes.erl:78: The call contracts_with_subtypes:foo2(5) breaks the contract (Arg1) -> Res when is_subtype(Arg1,Arg2), is_subtype(Arg2,atom()), is_subtype(Res,atom())
+contracts_with_subtypes.erl:79: The call contracts_with_subtypes:foo3(5) breaks the contract (Arg1) -> Res when is_subtype(Arg2,atom()), is_subtype(Arg1,Arg2), is_subtype(Res,atom())
+contracts_with_subtypes.erl:7: Invalid type specification for function contracts_with_subtypes:extract/0. The success typing is () -> 'something'
+contracts_with_subtypes.erl:80: The call contracts_with_subtypes:foo4(5) breaks the contract (Type) -> Type when is_subtype(Type,atom())
+contracts_with_subtypes.erl:81: The call contracts_with_subtypes:foo5(5) breaks the contract (Type::atom()) -> Type::atom()
+contracts_with_subtypes.erl:82: The call contracts_with_subtypes:foo6(5) breaks the contract (Type) -> Type when is_subtype(Type,atom())
diff --git a/lib/dialyzer/test/small_SUITE_data/results/port_info_test b/lib/dialyzer/test/small_SUITE_data/results/port_info_test
index 9ee863f9eb..863a3d61df 100644
--- a/lib/dialyzer/test/small_SUITE_data/results/port_info_test
+++ b/lib/dialyzer/test/small_SUITE_data/results/port_info_test
@@ -3,4 +3,5 @@ port_info_test.erl:10: The pattern {'connected', 42} can never match the type 'u
port_info_test.erl:14: The pattern {'registered_name', "42"} can never match the type 'undefined' | {'registered_name',atom()}
port_info_test.erl:19: The pattern {'output', 42} can never match the type 'undefined' | {'connected',pid()}
port_info_test.erl:24: Guard test 'links' =:= Atom::'connected' can never succeed
-port_info_test.erl:28: The pattern {'gazonk', _} can never match the type 'undefined' | {'connected' | 'id' | 'input' | 'links' | 'name' | 'output' | 'registered_name',atom() | pid() | [pid() | char()] | integer()}
+port_info_test.erl:28: The pattern {'gazonk', _} can never match the type 'undefined' | {'connected' | 'id' | 'input' | 'links' | 'name' | 'os_pid' | 'output' | 'registered_name',atom() | pid() | [pid() | char()] | integer()}
+port_info_test.erl:32: The pattern {'os_pid', "42"} can never match the type 'undefined' | {'os_pid','undefined' | non_neg_integer()}
diff --git a/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/a.erl b/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/a.erl
new file mode 100644
index 0000000000..7efe870b0d
--- /dev/null
+++ b/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/a.erl
@@ -0,0 +1,9 @@
+-module(a).
+-export([g/1]).
+
+-export_type([a/0, t/0]).
+-type a() :: integer().
+-type t() :: a() | maybe_improper_list(t(), t()).
+
+-spec g(t()) -> t().
+g(X) -> X.
diff --git a/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/b.erl b/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/b.erl
new file mode 100644
index 0000000000..b08bc5e66c
--- /dev/null
+++ b/lib/dialyzer/test/small_SUITE_data/src/collapse_lists/b.erl
@@ -0,0 +1,5 @@
+-module(b).
+-export([f/1]).
+
+-spec f(a:t()) -> a:t().
+f(X) -> a:g(X).
diff --git a/lib/dialyzer/test/small_SUITE_data/src/contracts_with_subtypes.erl b/lib/dialyzer/test/small_SUITE_data/src/contracts_with_subtypes.erl
new file mode 100644
index 0000000000..d72138d509
--- /dev/null
+++ b/lib/dialyzer/test/small_SUITE_data/src/contracts_with_subtypes.erl
@@ -0,0 +1,267 @@
+-module(contracts_with_subtypes).
+
+-compile(export_all).
+
+%===============================================================================
+
+-spec extract() -> 'ok'.
+
+extract() ->
+ case dz_extract() of
+ {ok, Val} -> Val;
+ error -> exit(boom)
+ end.
+
+-spec dz_extract() -> RetValue when
+ FileList :: something,
+ RetValue :: {ok, FileList} | error.
+
+dz_extract() -> get(foo).
+
+%-------------------------------------------------------------------------------
+
+-spec extract2() -> 'ok'.
+
+extract2() ->
+ case dz_extract2() of
+ {ok, Val} -> Val;
+ error -> exit(boom)
+ end.
+
+-spec dz_extract2() -> RetValue when
+ RetValue :: {ok, FileList} | error,
+ FileList :: something.
+
+dz_extract2() -> get(foo).
+
+%===============================================================================
+
+-spec foo1(Arg1) -> Res when
+ Arg1 :: atom(),
+ Res :: atom().
+
+foo1(X) -> X.
+
+-spec foo2(Arg1) -> Res when
+ Arg1 :: Arg2,
+ Arg2 :: atom(),
+ Res :: atom().
+
+foo2(X) -> X.
+
+-spec foo3(Arg1) -> Res when
+ Arg2 :: atom(),
+ Arg1 :: Arg2,
+ Res :: atom().
+
+foo3(X) -> X.
+
+-spec foo4(Type) -> Type when is_subtype(Type, atom()).
+
+foo4(X) -> X.
+
+-spec foo5(Type :: atom()) -> Type :: atom().
+
+foo5(X) -> X.
+
+-spec foo6(Type) -> Type when Type :: atom().
+
+foo6(X) -> X.
+
+-spec foo7(Type) -> Type.
+
+foo7(X) -> X.
+
+%-------------------------------------------------------------------------------
+
+bar(1) -> foo1(5);
+bar(2) -> foo2(5);
+bar(3) -> foo3(5);
+bar(4) -> foo4(5);
+bar(5) -> foo5(5);
+bar(6) -> foo6(5);
+bar(7) -> foo7(5).
+
+wrong_foo6() ->
+ b = foo6(a).
+
+%===============================================================================
+
+-spec rec_arg(Arg) -> ok when
+ Arg :: {a, A} | {b, B},
+ A :: a | {b, B},
+ B :: b | {a, A}.
+
+rec_arg(X) -> get(X).
+
+c(aa) -> rec_arg({a, a});
+c(bb) -> rec_arg({b, b});
+c(abb) -> rec_arg({a, {b, b}});
+c(baa) -> rec_arg({b, {a, a}});
+c(abaa) -> rec_arg({a, {b, {a, a}}});
+c(babb) -> rec_arg({b, {a, {b, b}}});
+c(ababb) -> rec_arg({a, {b, {a, {b, b}}}});
+c(babaa) -> rec_arg({b, {a, {b, {a, a}}}}).
+
+w(ab) -> rec_arg({a, b});
+w(ba) -> rec_arg({b, a});
+w(aba) -> rec_arg({a, {b, a}});
+w(bab) -> rec_arg({b, {a, b}});
+w(abab) -> rec_arg({a, {b, {a, b}}});
+w(baba) -> rec_arg({b, {a, {b, a}}});
+w(ababa) -> rec_arg({a, {b, {a, {b, a}}}});
+w(babab) -> rec_arg({b, {a, {b, {a, b}}}}).
+
+%===============================================================================
+
+-type dublo(X) :: {X, X}.
+
+-type weird(X,Y) :: {X, Y, X, X}.
+
+-spec forfun(dublo(Var)) -> ok when Var :: atom().
+
+forfun(_) -> ok.
+
+-spec forfun2(weird(Var, Var)) -> ok when Var :: atom().
+
+forfun2(_) -> ok.
+
+%===============================================================================
+
+-spec shallow(X) -> {ok, X} | {ok, X, file:filename()} | err1 | err2.
+
+shallow(X) -> get(X).
+
+st(X) when is_atom(X) ->
+ case shallow(X) of
+ err1 -> ok;
+ err2 -> ok;
+ {ok, X} -> ok;
+ {ok, X, Res} ->
+ case Res of
+ 1 -> bad;
+ _Other -> ok
+ end;
+ alpha -> bad;
+ {ok, 42} -> bad;
+ 42 -> bad
+ end.
+
+%-------------------------------------------------------------------------------
+
+-spec deep(X) -> Ret when
+ Ret :: {ok, X} | Err,
+ Err :: err1 | err2.
+
+deep(X) -> get(X).
+
+dt(X) when is_atom(X) ->
+ case deep(X) of
+ err1 -> ok;
+ err2 -> ok;
+ {ok, X} -> ok;
+ alpha -> bad;
+ {ok, 42} -> bad;
+ 42 -> bad
+ end.
+
+%-------------------------------------------------------------------------------
+
+-type local_errors() :: err1 | err2.
+
+-spec deep2(X) -> Ret when
+ Ret :: {ok, X} | Err,
+ Err :: local_errors().
+
+deep2(X) -> get(X).
+
+dt2(X) when is_atom(X) ->
+ case deep2(X) of
+ err1 -> ok;
+ err2 -> ok;
+ {ok, X} -> ok;
+ alpha -> bad;
+ {ok, 42} -> bad;
+ 42 -> bad
+ end.
+
+%-------------------------------------------------------------------------------
+
+-spec deep3(X) -> Ret when
+ Ret :: {ok, X, file:filename()} | Err,
+ Err :: local_errors().
+
+deep3(X) -> get(X).
+
+dt3(X) when is_atom(X) ->
+ case deep3(X) of
+ err1 -> ok;
+ err2 -> ok;
+ {ok, X, Res} ->
+ case Res of
+ 1 -> bad;
+ _Other -> ok
+ end;
+ {ok, X} -> bad;
+ alpha -> bad;
+ {ok, 42} -> bad;
+ 42 -> bad
+ end.
+
+%===============================================================================
+
+-spec flat_ets_new(Name, Options) -> atom() when
+ Name :: atom(),
+ Options :: [Option],
+ Option :: set
+ | ordered_set
+ | bag
+ | duplicate_bag
+ | public
+ | protected
+ | private
+ | named_table
+ | {keypos, integer()}
+ | {heir, pid(), term()}
+ | {heir, none}
+ | {write_concurrency, boolean()}
+ | {read_concurrency, boolean()}
+ | compressed.
+
+flat_ets_new(Name, Options) ->
+ get({Name, Options}).
+
+flat_ets_new_t() ->
+ flat_ets_new(12,[]),
+ flat_ets_new({a,b},[]),
+ flat_ets_new(name,[foo]),
+ flat_ets_new(name,{bag}),
+ flat_ets_new(name,bag),
+ ok.
+
+-type access() :: public | protected | private.
+-type type() :: set | ordered_set | bag | duplicate_bag.
+
+-spec factored_ets_new(Name, Options) -> atom() when
+ Name :: atom(),
+ Options :: [Option],
+ Option :: Type | Access | named_table | {keypos,Pos}
+ | {heir, Pid :: pid(), HeirData} | {heir, none} | Tweaks,
+ Type :: type(),
+ Access :: access(),
+ Tweaks :: {write_concurrency, boolean()}
+ | {read_concurrency, boolean()}
+ | compressed,
+ Pos :: pos_integer(),
+ HeirData :: term().
+
+factored_ets_new(Name, Options) ->
+ get({Name, Options}).
+
+factored_ets_new_t() ->
+ factored_ets_new(12,[]),
+ factored_ets_new({a,b},[]),
+ factored_ets_new(name,[foo]),
+ factored_ets_new(name,{bag}),
+ factored_ets_new(name,bag),
+ ok.
diff --git a/lib/dialyzer/test/small_SUITE_data/src/deep_lc.erl b/lib/dialyzer/test/small_SUITE_data/src/deep_lc.erl
new file mode 100644
index 0000000000..d9ca0817d9
--- /dev/null
+++ b/lib/dialyzer/test/small_SUITE_data/src/deep_lc.erl
@@ -0,0 +1,14 @@
+-module(deep_lc).
+
+-export([t/0]).
+
+%% This is compile/test/lc_SUITE:deeply_nested/1
+%%
+%% Used to be _very_ slow. Unknown how slow, but more than 15 hours.
+
+t() ->
+ [[X1,X2,X3,X4,X5,X6,X7(),X8,X9,X10,X11,X12,X13,X14,X15,X16,X17,X18(),X19,X20] ||
+ X1 <- [99],X2 <- [98],X3 <- [97],X4 <- [96],X5 <- [42],X6 <- [17],
+ X7 <- [fun() -> X5*X5 end],X8 <- [12],X9 <- [11],X10 <- [10],
+ X11 <- [9],X12 <- [8],X13 <- [7],X14 <- [6],X15 <- [5],
+ X16 <- [4],X17 <- [3],X18 <- [fun() -> X16+X17 end],X19 <- [2],X20 <- [1]].
diff --git a/lib/dialyzer/test/small_SUITE_data/src/port_info_test.erl b/lib/dialyzer/test/small_SUITE_data/src/port_info_test.erl
index 2ee9a3a6e2..07f22256c9 100644
--- a/lib/dialyzer/test/small_SUITE_data/src/port_info_test.erl
+++ b/lib/dialyzer/test/small_SUITE_data/src/port_info_test.erl
@@ -3,7 +3,7 @@
%% and the quality of the warnings that Dialyzer spits out
%%
-module(port_info_test).
--export([t1/1, t2/1, t3/1, t4/1, t5/2, buggy/1]).
+-export([t1/1, t2/1, t3/1, t4/1, t5/2, t6/1, buggy/1]).
%% The following errors are correctly caught, but the messages are a bit weird
t1(X) when is_port(X) ->
@@ -28,6 +28,10 @@ t5(X, Atom) when is_port(X) ->
{gazonk, _} = erlang:port_info(X, Atom);
t5(_, _) -> ok.
+t6(X) when is_port(X) ->
+ {os_pid, "42"} = erlang:port_info(X, os_pid);
+t6(_) -> ok.
+
%% The type system is not strong enough to catch the following errors
buggy(X) when is_atom(X) ->
{links, X} = erlang:port_info(foo, X).
diff --git a/lib/diameter/autoconf/vxworks/sed.general b/lib/diameter/autoconf/vxworks/sed.general
index 77b306aa0a..9199983e16 100644
--- a/lib/diameter/autoconf/vxworks/sed.general
+++ b/lib/diameter/autoconf/vxworks/sed.general
@@ -66,7 +66,6 @@ s|@HCLIBS@||
s|@ENABLE_ALLOC_TYPE_VARS@||
s|@TERMCAP_LIB@||
s|@ERTS_BUILD_SMP_EMU@|no|
-s|@ERTS_BUILD_HYBRID_EMU@|no|
s|@HAVE_VALGRIND@|no|
s|@EXEEXT@||
s|@WITH_SCTP@||
diff --git a/lib/diameter/doc/src/Makefile b/lib/diameter/doc/src/Makefile
index bc3e649e6b..cdf63e7fb6 100644
--- a/lib/diameter/doc/src/Makefile
+++ b/lib/diameter/doc/src/Makefile
@@ -162,18 +162,18 @@ include $(DIAMETER_TOP)/make/release_targets.mk
endif
release_docs_spec: $(LOCAL)docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man1
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man4
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(HTMLDIR)/*.* $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DATA) $(MAN1_FILES) $(RELEASE_PATH)/man/man1
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN4_FILES) $(RELEASE_PATH)/man/man4
- [ -z "$(LOCAL)" ] || cp -r $(HTMLDIR)/js $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man4"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(HTMLDIR)/*.* "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(MAN1_FILES) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN4_FILES) "$(RELEASE_PATH)/man/man4"
+ [ -z "$(LOCAL)" ] || cp -r $(HTMLDIR)/js "$(RELSYSDIR)/doc/html"
echo $(LOCAL)
release_spec:
diff --git a/lib/diameter/src/Makefile b/lib/diameter/src/Makefile
index dbfaa4e140..de2eca0279 100644
--- a/lib/diameter/src/Makefile
+++ b/lib/diameter/src/Makefile
@@ -195,27 +195,27 @@ endif
release_spec: opt
for d in bin ebin include src/dict; do \
- $(INSTALL_DIR) $(RELSYSDIR)/$$d; \
+ $(INSTALL_DIR) "$(RELSYSDIR)/$$d"; \
done
- $(INSTALL_SCRIPT) $(BINS:%=../bin/%) $(RELSYSDIR)/bin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_SCRIPT) $(BINS:%=../bin/%) "$(RELSYSDIR)/bin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(EXTERNAL_HRLS:%=../include/%) $(DICT_HRLS) \
- $(RELSYSDIR)/include
- $(INSTALL_DATA) $(DICTS:%=dict/%.dia) $(RELSYSDIR)/src/dict
+ "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(DICTS:%=dict/%.dia) "$(RELSYSDIR)/src/dict"
$(MAKE) $(TARGET_DIRS:%/=release_src_%)
$(MAKE) $(EXAMPLE_DIRS:%/=release_examples_%)
$(TARGET_DIRS:%/=release_src_%): release_src_%:
- $(INSTALL_DIR) $(RELSYSDIR)/src/$*
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/$*"
$(INSTALL_DATA) $(filter $*/%, $(TARGET_MODULES:%=%.erl) \
$(INTERNAL_HRLS)) \
$(filter $*/%, compiler/$(DICT_YRL).yrl) \
- $(RELSYSDIR)/src/$*
+ "$(RELSYSDIR)/src/$*"
$(EXAMPLE_DIRS:%/=release_examples_%): release_examples_%:
- $(INSTALL_DIR) $(RELSYSDIR)/examples/$*
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/$*"
$(INSTALL_DATA) $(patsubst %, ../examples/%, $(filter $*/%, $(EXAMPLES))) \
- $(RELSYSDIR)/examples/$*
+ "$(RELSYSDIR)/examples/$*"
release_docs_spec:
diff --git a/lib/diameter/test/Makefile b/lib/diameter/test/Makefile
index ab5b45ff3d..1659330a91 100644
--- a/lib/diameter/test/Makefile
+++ b/lib/diameter/test/Makefile
@@ -141,7 +141,7 @@ log:
# ----------------------------------------------------
/%: % force
- sed -f release.sed $< > $(RELSYSDIR)$@
+ sed -f release.sed $< > "$(RELSYSDIR)$@"
ifeq ($(ERL_TOP),)
include $(DIAMETER_TOP)/make/release_targets.mk
@@ -152,17 +152,17 @@ endif
release_spec release_docs_spec:
release_tests_spec:
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(TEST_SPEC_FILE) \
$(COVER_SPEC_FILE) \
$(HRL_FILES) \
- $(RELSYSDIR)
+ "$(RELSYSDIR)"
$(MAKE) $(DATA_DIRS:%/=release_data_%)
$(MAKE) $(ERL_FILES:%=/%)
$(DATA_DIRS:%/=release_data_%): release_data_%:
- $(INSTALL_DIR) $(RELSYSDIR)/$*
- $(INSTALL_DATA) $(filter $*/%, $(DATA)) $(RELSYSDIR)/$*
+ $(INSTALL_DIR) "$(RELSYSDIR)/$*"
+ $(INSTALL_DATA) $(filter $*/%, $(DATA)) "$(RELSYSDIR)/$*"
force:
diff --git a/lib/edoc/doc/src/Makefile b/lib/edoc/doc/src/Makefile
index b933094464..1f92d36f12 100644
--- a/lib/edoc/doc/src/Makefile
+++ b/lib/edoc/doc/src/Makefile
@@ -124,13 +124,13 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/edoc/include/Makefile b/lib/edoc/include/Makefile
index 5b2ad38c9d..cf2e051632 100644
--- a/lib/edoc/include/Makefile
+++ b/lib/edoc/include/Makefile
@@ -49,8 +49,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(INCLUDE_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(INCLUDE_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/edoc/priv/Makefile b/lib/edoc/priv/Makefile
index 13225e6d1a..73c42c05eb 100644
--- a/lib/edoc/priv/Makefile
+++ b/lib/edoc/priv/Makefile
@@ -45,9 +45,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(PRIV_FILES) $(RELSYSDIR)/priv
- $(INSTALL_SCRIPT) $(GEN_SCRIPT) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(PRIV_FILES) "$(RELSYSDIR)/priv"
+ $(INSTALL_SCRIPT) $(GEN_SCRIPT) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/edoc/src/Makefile b/lib/edoc/src/Makefile
index fcb0b61292..72354ac711 100644
--- a/lib/edoc/src/Makefile
+++ b/lib/edoc/src/Makefile
@@ -85,10 +85,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(OBJECTS) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(SOURCES) $(HRL_FILES) $(YRL_FILE) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(OBJECTS) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(SOURCES) $(HRL_FILES) $(YRL_FILE) "$(RELSYSDIR)/src"
release_docs_spec:
diff --git a/lib/edoc/test/Makefile b/lib/edoc/test/Makefile
index 2dbdb77eff..2033e003b3 100644
--- a/lib/edoc/test/Makefile
+++ b/lib/edoc/test/Makefile
@@ -57,10 +57,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) edoc.spec edoc.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) edoc.spec edoc.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/eldap/.gitignore b/lib/eldap/.gitignore
index 5585418186..d3dd8228d5 100644
--- a/lib/eldap/.gitignore
+++ b/lib/eldap/.gitignore
@@ -1,4 +1,4 @@
*.beam
*.asn1db
-src/ELDAPv3.hrl
-src/ELDAPv3.erl
+ebin/ELDAPv3.hrl
+ebin/ELDAPv3.erl
diff --git a/lib/eldap/doc/src/Makefile b/lib/eldap/doc/src/Makefile
index 4c827319b4..a4827793f4 100644
--- a/lib/eldap/doc/src/Makefile
+++ b/lib/eldap/doc/src/Makefile
@@ -99,16 +99,16 @@ clean clean_docs clean_tex:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
-# $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
-# $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+# $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+# $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/eldap/src/Makefile b/lib/eldap/src/Makefile
index 4ddb8082d7..39a41d08e2 100644
--- a/lib/eldap/src/Makefile
+++ b/lib/eldap/src/Makefile
@@ -96,14 +96,14 @@ $(ASN1_HRL): ../asn1/$(ASN1_FILES)
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/asn1
- $(INSTALL_DATA) ../asn1/$(ASN1_FILES) $(RELSYSDIR)/asn1
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/asn1"
+ $(INSTALL_DATA) ../asn1/$(ASN1_FILES) "$(RELSYSDIR)/asn1"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/eldap/test/Makefile b/lib/eldap/test/Makefile
index a17d4f56b2..3c5810eece 100644
--- a/lib/eldap/test/Makefile
+++ b/lib/eldap/test/Makefile
@@ -50,7 +50,7 @@ RELSYSDIR = $(RELEASE_PATH)/eldap_test
# ----------------------------------------------------
# FLAGS
# ----------------------------------------------------
-ERL_COMPILE_FLAGS += $(INCLUDES)
+ERL_COMPILE_FLAGS += $(INCLUDES) -pa $(ERL_TOP)/lib/eldap/ebin
EBIN = .
@@ -75,9 +75,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(SPEC_FILES) $(ERL_FILES) $(COVER_FILE) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
-# @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SPEC_FILES) $(ERL_FILES) $(COVER_FILE) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+# @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/erl_docgen/doc/src/Makefile b/lib/erl_docgen/doc/src/Makefile
index ff50c12895..a254c4fb6d 100644
--- a/lib/erl_docgen/doc/src/Makefile
+++ b/lib/erl_docgen/doc/src/Makefile
@@ -124,13 +124,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/erl_docgen/doc/src/notes.xml b/lib/erl_docgen/doc/src/notes.xml
index 23f64b876a..8ca11b1cf5 100644
--- a/lib/erl_docgen/doc/src/notes.xml
+++ b/lib/erl_docgen/doc/src/notes.xml
@@ -30,7 +30,60 @@
</header>
<p>This document describes the changes made to the <em>erl_docgen</em> application.</p>
- <section><title>Erl_Docgen 0.3</title>
+ <section><title>Erl_Docgen 0.3.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p> Some links in C libraries were not generated
+ correctly. This bug has been fixed. </p>
+ <p>
+ Own Id: OTP-9832</p>
+ </item>
+ <item>
+ <p>
+ Set `font-family: Courier, monospace' in OTP doc CSS</p>
+ <p>
+ left Courier as the primary original font and also added
+ monospace as secondary for people which in Linux does not
+ have it installed.</p>
+ <p>
+ Also adds minor cosmetic changes to the CSS. (Thanks to
+ Ricardo Catalinas Jim�nez)</p>
+ <p>
+ Own Id: OTP-9918</p>
+ </item>
+ <item>
+ <p>
+ When generating from edoc it is now possible to use
+ ranges in specs and &lt;img&gt; tags in the description.</p>
+ <p>
+ Own Id: OTP-9970</p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p> Optimize and improve handling of multiple func:s.
+ </p>
+ <p>
+ Own Id: OTP-9877</p>
+ </item>
+ <item>
+ <p> The generation of the libraries' HTML documentation
+ has been optimized. </p>
+ <p>
+ Own Id: OTP-9893</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>Erl_Docgen 0.3</title>
<section><title>Fixed Bugs and Malfunctions</title>
<list>
diff --git a/lib/erl_docgen/priv/bin/Makefile b/lib/erl_docgen/priv/bin/Makefile
index 95ad36216a..449cc6691c 100644
--- a/lib/erl_docgen/priv/bin/Makefile
+++ b/lib/erl_docgen/priv/bin/Makefile
@@ -64,8 +64,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_SCRIPT) $(ESCRIPT_FILES) $(RELSYSDIR)/priv/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_SCRIPT) $(ESCRIPT_FILES) "$(RELSYSDIR)/priv/bin"
release_docs_spec:
diff --git a/lib/erl_docgen/priv/css/Makefile b/lib/erl_docgen/priv/css/Makefile
index 81124fb111..0faca019f3 100644
--- a/lib/erl_docgen/priv/css/Makefile
+++ b/lib/erl_docgen/priv/css/Makefile
@@ -64,13 +64,13 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/css
- $(INSTALL_DATA) $(CSS_FILES) $(RELSYSDIR)/priv/css
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/css"
+ $(INSTALL_DATA) $(CSS_FILES) "$(RELSYSDIR)/priv/css"
release_docs_spec:
- $(INSTALL_DIR) $(RELEASE_PATH)/doc
- $(INSTALL_DATA) $(CSS_FILES) ../nyi.html $(RELEASE_PATH)/doc
+ $(INSTALL_DIR) "$(RELEASE_PATH)/doc"
+ $(INSTALL_DATA) $(CSS_FILES) ../nyi.html "$(RELEASE_PATH)/doc"
release_tests_spec:
diff --git a/lib/erl_docgen/priv/dtd/Makefile b/lib/erl_docgen/priv/dtd/Makefile
index 65c68fcca7..314374d34b 100644
--- a/lib/erl_docgen/priv/dtd/Makefile
+++ b/lib/erl_docgen/priv/dtd/Makefile
@@ -89,8 +89,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/dtd
- $(INSTALL_DATA) $(DTD_FILES) $(ENT_FILES) $(RELSYSDIR)/priv/dtd
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/dtd"
+ $(INSTALL_DATA) $(DTD_FILES) $(ENT_FILES) "$(RELSYSDIR)/priv/dtd"
release_docs_spec:
diff --git a/lib/erl_docgen/priv/dtd_html_entities/Makefile b/lib/erl_docgen/priv/dtd_html_entities/Makefile
index d57302bd1b..9cd3f38c4b 100644
--- a/lib/erl_docgen/priv/dtd_html_entities/Makefile
+++ b/lib/erl_docgen/priv/dtd_html_entities/Makefile
@@ -63,8 +63,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/dtd_html_entities
- $(INSTALL_DATA) $(ENTITY_FILES) $(RELSYSDIR)/priv/dtd_html_entities
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/dtd_html_entities"
+ $(INSTALL_DATA) $(ENTITY_FILES) "$(RELSYSDIR)/priv/dtd_html_entities"
release_docs_spec:
diff --git a/lib/erl_docgen/priv/dtd_man_entities/Makefile b/lib/erl_docgen/priv/dtd_man_entities/Makefile
index 5651d8bc29..b6f29af6b4 100644
--- a/lib/erl_docgen/priv/dtd_man_entities/Makefile
+++ b/lib/erl_docgen/priv/dtd_man_entities/Makefile
@@ -63,8 +63,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/dtd_man_entities
- $(INSTALL_DATA) $(ENTITY_FILES) $(RELSYSDIR)/priv/dtd_man_entities
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/dtd_man_entities"
+ $(INSTALL_DATA) $(ENTITY_FILES) "$(RELSYSDIR)/priv/dtd_man_entities"
release_docs_spec:
diff --git a/lib/erl_docgen/priv/images/Makefile b/lib/erl_docgen/priv/images/Makefile
index 8b858fefb3..389f9f98ae 100644
--- a/lib/erl_docgen/priv/images/Makefile
+++ b/lib/erl_docgen/priv/images/Makefile
@@ -66,13 +66,13 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/images
- $(INSTALL_DATA) $(GIF_FILES) $(PNG_FILES) $(RELSYSDIR)/priv/images
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/images"
+ $(INSTALL_DATA) $(GIF_FILES) $(PNG_FILES) "$(RELSYSDIR)/priv/images"
release_docs_spec:
- $(INSTALL_DIR) $(RELEASE_PATH)/doc
- $(INSTALL_DATA) $(PNG_FILES) $(RELEASE_PATH)/doc
+ $(INSTALL_DIR) "$(RELEASE_PATH)/doc"
+ $(INSTALL_DATA) $(PNG_FILES) "$(RELEASE_PATH)/doc"
release_tests_spec:
diff --git a/lib/erl_docgen/priv/js/flipmenu/Makefile b/lib/erl_docgen/priv/js/flipmenu/Makefile
index 65c5c91f35..682d186608 100644
--- a/lib/erl_docgen/priv/js/flipmenu/Makefile
+++ b/lib/erl_docgen/priv/js/flipmenu/Makefile
@@ -68,13 +68,13 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/js/flipmenu
- $(INSTALL_DATA) $(JS_FILES) $(GIF_FILES) $(RELSYSDIR)/priv/js/flipmenu
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/js/flipmenu"
+ $(INSTALL_DATA) $(JS_FILES) $(GIF_FILES) "$(RELSYSDIR)/priv/js/flipmenu"
release_docs_spec:
- $(INSTALL_DIR) $(RELEASE_PATH)/doc/js/flipmenu
- $(INSTALL_DATA) $(JS_FILES) $(GIF_FILES) $(RELEASE_PATH)/doc/js/flipmenu
+ $(INSTALL_DIR) "$(RELEASE_PATH)/doc/js/flipmenu"
+ $(INSTALL_DATA) $(JS_FILES) $(GIF_FILES) "$(RELEASE_PATH)/doc/js/flipmenu"
release_tests_spec:
diff --git a/lib/erl_docgen/priv/xsl/Makefile b/lib/erl_docgen/priv/xsl/Makefile
index 92a53b8c0b..ca7a4e8157 100644
--- a/lib/erl_docgen/priv/xsl/Makefile
+++ b/lib/erl_docgen/priv/xsl/Makefile
@@ -68,8 +68,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/xsl
- $(INSTALL_DATA) $(XSL_FILES) $(RELSYSDIR)/priv/xsl
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/xsl"
+ $(INSTALL_DATA) $(XSL_FILES) "$(RELSYSDIR)/priv/xsl"
release_docs_spec:
diff --git a/lib/erl_docgen/priv/xsl/db_pdf.xsl b/lib/erl_docgen/priv/xsl/db_pdf.xsl
index 4ed4fa14c4..bf17406d84 100644
--- a/lib/erl_docgen/priv/xsl/db_pdf.xsl
+++ b/lib/erl_docgen/priv/xsl/db_pdf.xsl
@@ -1564,7 +1564,7 @@
</xsl:variable>
<fo:block xsl:use-attribute-sets="image">
- <fo:external-graphic content-width="60%" src="{@file}"/>
+ <fo:external-graphic content-width="scale-down-to-fit" inline-progression-dimension.maximum="100%" src="{@file}"/>
<xsl:apply-templates>
<xsl:with-param name="chapnum" select="$chapnum"/>
diff --git a/lib/erl_docgen/src/Makefile b/lib/erl_docgen/src/Makefile
index cbaf6e4627..4d8f43bfed 100644
--- a/lib/erl_docgen/src/Makefile
+++ b/lib/erl_docgen/src/Makefile
@@ -89,10 +89,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/erl_docgen/vsn.mk b/lib/erl_docgen/vsn.mk
index dbd7e017b0..bf10591f34 100644
--- a/lib/erl_docgen/vsn.mk
+++ b/lib/erl_docgen/vsn.mk
@@ -1,2 +1,2 @@
-ERL_DOCGEN_VSN = 0.3
+ERL_DOCGEN_VSN = 0.3.1
diff --git a/lib/erl_interface/doc/src/Makefile b/lib/erl_interface/doc/src/Makefile
index e05b647cb2..2bad8976b5 100644
--- a/lib/erl_interface/doc/src/Makefile
+++ b/lib/erl_interface/doc/src/Makefile
@@ -113,16 +113,16 @@ clean clean_docs clean_tex:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man1
- $(INSTALL_DATA) $(MAN1_FILES) $(RELEASE_PATH)/man/man1
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DATA) $(MAN1_FILES) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/erl_interface/doc/src/notes.xml b/lib/erl_interface/doc/src/notes.xml
index 4cb9532880..48ac0be22d 100644
--- a/lib/erl_interface/doc/src/notes.xml
+++ b/lib/erl_interface/doc/src/notes.xml
@@ -30,6 +30,21 @@
</header>
<p>This document describes the changes made to the Erl_interface application.</p>
+<section><title>Erl_Interface 3.7.7</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>Minor suppressions and fixes of compilation
+ warnings</p>
+ <p>
+ Own Id: OTP-10016</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Erl_Interface 3.7.6</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/erl_interface/src/Makefile.in b/lib/erl_interface/src/Makefile.in
index d6b0ca1f16..661dbb68ac 100644
--- a/lib/erl_interface/src/Makefile.in
+++ b/lib/erl_interface/src/Makefile.in
@@ -843,32 +843,32 @@ EXTRA = \
$(TARGET)/eidefs.mk
release: opt
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/lib
- $(INSTALL_DIR) $(RELSYSDIR)/bin
- $(INSTALL_DIR) $(RELSYSDIR)/src/auxdir
- $(INSTALL_DIR) $(RELSYSDIR)/src/connect
- $(INSTALL_DIR) $(RELSYSDIR)/src/decode
- $(INSTALL_DIR) $(RELSYSDIR)/src/encode
- $(INSTALL_DIR) $(RELSYSDIR)/src/epmd
- $(INSTALL_DIR) $(RELSYSDIR)/src/legacy
- $(INSTALL_DIR) $(RELSYSDIR)/src/misc
- $(INSTALL_DIR) $(RELSYSDIR)/src/prog
- $(INSTALL_DIR) $(RELSYSDIR)/src/registry
- $(INSTALL_DATA) $(HEADERS) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(OBJ_TARGETS) $(RELSYSDIR)/lib
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/lib"
+ $(INSTALL_DIR) "$(RELSYSDIR)/bin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/auxdir"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/connect"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/decode"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/encode"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/epmd"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/legacy"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/misc"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/prog"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/registry"
+ $(INSTALL_DATA) $(HEADERS) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(OBJ_TARGETS) "$(RELSYSDIR)/lib"
ifneq ($(EXE_TARGETS),)
- $(INSTALL_PROGRAM) $(EXE_TARGETS) $(RELSYSDIR)/bin
-endif
- $(INSTALL_DATA) $(EXTRA) $(RELSYSDIR)/src
- $(INSTALL_DATA) connect/*.[ch] $(RELSYSDIR)/src/connect
- $(INSTALL_DATA) decode/*.[ch] $(RELSYSDIR)/src/decode
- $(INSTALL_DATA) encode/*.[ch] $(RELSYSDIR)/src/encode
- $(INSTALL_DATA) epmd/*.[ch] $(RELSYSDIR)/src/epmd
- $(INSTALL_DATA) misc/*.[ch] $(RELSYSDIR)/src/misc
- $(INSTALL_DATA) registry/*.[ch] $(RELSYSDIR)/src/registry
- $(INSTALL_DATA) legacy/*.[ch] $(RELSYSDIR)/src/legacy
- $(INSTALL_DATA) prog/*.[ch] $(RELSYSDIR)/src/prog
+ $(INSTALL_PROGRAM) $(EXE_TARGETS) "$(RELSYSDIR)/bin"
+endif
+ $(INSTALL_DATA) $(EXTRA) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) connect/*.[ch] "$(RELSYSDIR)/src/connect"
+ $(INSTALL_DATA) decode/*.[ch] "$(RELSYSDIR)/src/decode"
+ $(INSTALL_DATA) encode/*.[ch] "$(RELSYSDIR)/src/encode"
+ $(INSTALL_DATA) epmd/*.[ch] "$(RELSYSDIR)/src/epmd"
+ $(INSTALL_DATA) misc/*.[ch] "$(RELSYSDIR)/src/misc"
+ $(INSTALL_DATA) registry/*.[ch] "$(RELSYSDIR)/src/registry"
+ $(INSTALL_DATA) legacy/*.[ch] "$(RELSYSDIR)/src/legacy"
+ $(INSTALL_DATA) prog/*.[ch] "$(RELSYSDIR)/src/prog"
release_docs:
diff --git a/lib/erl_interface/test/Makefile b/lib/erl_interface/test/Makefile
index 4faf89c0d6..d11a138844 100644
--- a/lib/erl_interface/test/Makefile
+++ b/lib/erl_interface/test/Makefile
@@ -71,9 +71,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(SPEC_FILES) $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SPEC_FILES) $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/erl_interface/test/all_SUITE_data/Makefile.src b/lib/erl_interface/test/all_SUITE_data/Makefile.src
index 70652e47c5..39085def2d 100644
--- a/lib/erl_interface/test/all_SUITE_data/Makefile.src
+++ b/lib/erl_interface/test/all_SUITE_data/Makefile.src
@@ -32,7 +32,7 @@ all: $(ALL_OBJS)
$(EI_COMMON_OBJS): gccifier@exe@
-@IFEQ@ (@erl_interface_cross_compile@, true)
+@IFEQ@ (@cross@, yes)
gccifier@exe@:
$(CP) gccifier.sh gccifier@exe@
$(CHMOD) a+x gccifier@exe@
diff --git a/lib/erl_interface/test/all_SUITE_data/gccifier.c b/lib/erl_interface/test/all_SUITE_data/gccifier.c
index 9f556fc4ed..a1019f9a72 100644
--- a/lib/erl_interface/test/all_SUITE_data/gccifier.c
+++ b/lib/erl_interface/test/all_SUITE_data/gccifier.c
@@ -1,7 +1,7 @@
/*
* %CopyrightBegin%
*
- * Copyright Ericsson AB 2005-2009. All Rights Reserved.
+ * Copyright Ericsson AB 2004-2009. 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
@@ -16,7 +16,6 @@
*
* %CopyrightEnd%
*
-
*/
/*
@@ -74,17 +73,23 @@ save_arg(args_t *args, char *arg1, ...)
args->vec = (char **) (args->no
? realloc((void *) args->vec,
(sizeof(char *)
- *(args->no + ARGS_INCR + 1)))
+ *(args->no + ARGS_INCR + 2)))
: malloc((sizeof(char *)
- *(args->no + ARGS_INCR + 1))));
+ *(args->no + ARGS_INCR + 2))));
if (!args->vec)
enomem();
args->no += ARGS_INCR;
}
+ if (carg == arg1) {
+ args->vec[args->ix++] = "\"";
+ args->chars++;
+ }
args->vec[args->ix++] = carg;
args->chars += strlen(carg);
carg = va_arg(argp, char *);
}
+ args->vec[args->ix++] = "\"";
+ args->chars++;
args->vec[args->ix++] = " ";
args->chars++;
va_end(argp);
@@ -232,6 +237,9 @@ main(int argc, char *argv[])
CHECK_FIRST_LINK_ARG;
save_arg(&link_args, "-libpath:", arg, NULL);
}
+ else if (strcmp("-link",arg) == 0) {
+ CHECK_FIRST_LINK_ARG;
+ }
#endif /* #ifdef __WIN32__ */
else if (is_prefix("-l", &arg)) {
CHECK_FIRST_LINK_ARG;
diff --git a/lib/erl_interface/test/all_SUITE_data/init_tc.erl b/lib/erl_interface/test/all_SUITE_data/init_tc.erl
index 7a599994fc..60c965eda3 100644
--- a/lib/erl_interface/test/all_SUITE_data/init_tc.erl
+++ b/lib/erl_interface/test/all_SUITE_data/init_tc.erl
@@ -48,8 +48,7 @@ run1(Name) ->
generate(TcName, Cases) ->
Hrl = TcName ++ "_cases.hrl",
{ok, HrlFile} = file:open(Hrl, write),
- {ok, Dir} = file:get_cwd(),
- generate_hrl(Cases, HrlFile, {filename:join(Dir, TcName), 0}),
+ generate_hrl(Cases, HrlFile, {TcName, 0}),
file:close(HrlFile),
C = TcName ++ "_decl.c",
{ok, CFile} = file:open(C, write),
@@ -57,7 +56,7 @@ generate(TcName, Cases) ->
file:close(CFile).
generate_hrl([Case|Rest], File, {Name, Number}) ->
- io:format(File, "-define(~s, {\"~s\", ~w}).~n", [Case, Name, Number]),
+ io:format(File, "-define(~s, {filename:join(proplists:get_value(data_dir,Config),\"~s\"), ~w}).~n", [Case, Name, Number]),
generate_hrl(Rest, File, {Name, Number+1});
generate_hrl([], _, _) ->
ok.
diff --git a/lib/erl_interface/test/ei_tmo_SUITE.erl b/lib/erl_interface/test/ei_tmo_SUITE.erl
index 7ff8c08280..cc22cb7440 100644
--- a/lib/erl_interface/test/ei_tmo_SUITE.erl
+++ b/lib/erl_interface/test/ei_tmo_SUITE.erl
@@ -88,12 +88,12 @@ ei_recv_tmo(doc) ->
ei_recv_tmo(suite) ->
[];
ei_recv_tmo(Config) when is_list(Config) ->
- ?line do_one_recv(c_node_recv_tmo_1),
- ?line do_one_recv_failure(c_node_recv_tmo_2),
+ ?line do_one_recv(Config,c_node_recv_tmo_1),
+ ?line do_one_recv_failure(Config,c_node_recv_tmo_2),
ok.
-do_one_recv(CNode) ->
+do_one_recv(Config,CNode) ->
?line {_,Host} = split(node()),
?line P1 = runner:start(?recv_tmo),
?line runner:send_term(P1,{CNode,
@@ -107,7 +107,7 @@ do_one_recv(CNode) ->
?line {term, Term1} = runner:get_term(P1, 10000),
?line runner:recv_eot(P1).
-do_one_recv_failure(CNode) ->
+do_one_recv_failure(Config,CNode) ->
?line P1 = runner:start(?recv_tmo),
?line runner:send_term(P1,{CNode,
erlang:get_cookie(),
@@ -128,14 +128,14 @@ ei_send_tmo(Config) when is_list(Config) ->
%dbg:p(self()),
VxSim = ?config(vxsim, Config),
?line register(ei_send_tmo_1,self()),
- ?line do_one_send(self(),c_node_send_tmo_1),
- ?line do_one_send(ei_send_tmo_1,c_node_send_tmo_2),
- ?line do_one_send_failure(self(),cccc1,c_nod_send_tmo_3,VxSim),
- ?line do_one_send_failure(ei_send_tmo_1,cccc2,c_nod_send_tmo_4,VxSim),
+ ?line do_one_send(Config,self(),c_node_send_tmo_1),
+ ?line do_one_send(Config,ei_send_tmo_1,c_node_send_tmo_2),
+ ?line do_one_send_failure(Config,self(),cccc1,c_nod_send_tmo_3,VxSim),
+ ?line do_one_send_failure(Config,ei_send_tmo_1,cccc2,c_nod_send_tmo_4,VxSim),
ok.
-do_one_send(From,CNode) ->
+do_one_send(Config,From,CNode) ->
?line {_,Host} = split(node()),
?line P1 = runner:start(?send_tmo),
?line runner:send_term(P1,{CNode,
@@ -155,7 +155,7 @@ do_one_send(From,CNode) ->
?line {term, 0} = runner:get_term(P1, 10000),
?line runner:recv_eot(P1).
-do_one_send_failure(From,FakeName,CName,VxSim) ->
+do_one_send_failure(Config,From,FakeName,CName,VxSim) ->
?line {_,Host} = split(node()),
?line OurName = join(FakeName,Host),
?line Node = join(CName,Host),
diff --git a/lib/erl_interface/test/erl_match_SUITE.erl b/lib/erl_interface/test/erl_match_SUITE.erl
index e019fecca8..edbb17a8c1 100644
--- a/lib/erl_interface/test/erl_match_SUITE.erl
+++ b/lib/erl_interface/test/erl_match_SUITE.erl
@@ -29,7 +29,7 @@
bind/1, integers/1, floats/1, binaries/1, strings/1]).
%% For interactive running of matcher.
--export([start_matcher/0, erl_match/3]).
+-export([start_matcher/1, erl_match/3]).
%% This test suite tests the erl_match() function.
@@ -57,7 +57,7 @@ end_per_group(_GroupName, Config) ->
atoms(suite) -> [];
atoms(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line eq(P, '', ''),
?line eq(P, a, a),
@@ -74,7 +74,7 @@ atoms(Config) when is_list(Config) ->
lists(suite) -> [];
lists(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line eq(P, [], []),
?line ne(P, [], [a]),
@@ -101,7 +101,7 @@ lists(Config) when is_list(Config) ->
tuples(suite) -> [];
tuples(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line ne(P, {}, {a, b}),
?line ne(P, {a, b}, {}),
@@ -129,7 +129,7 @@ tuples(Config) when is_list(Config) ->
references(suite) -> [];
references(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line Ref1 = make_ref(),
?line Ref2 = make_ref(),
@@ -144,7 +144,7 @@ references(Config) when is_list(Config) ->
pids(suite) -> [];
pids(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line Pid1 = c:pid(0,1,2),
?line Pid2 = c:pid(0,1,3),
@@ -163,8 +163,8 @@ ports(Config) when is_list(Config) ->
vxworks ->
{skipped,"not on vxworks, pucko"};
_ ->
- ?line P = start_matcher(),
- ?line P2 = start_matcher(),
+ ?line P = start_matcher(Config),
+ ?line P2 = start_matcher(Config),
?line eq(P, P, P),
?line ne(P, P, P2),
@@ -176,7 +176,7 @@ ports(Config) when is_list(Config) ->
integers(suite) -> [];
integers(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line I1 = 123,
?line I2 = 12345,
?line I3 = -123,
@@ -195,7 +195,7 @@ integers(Config) when is_list(Config) ->
floats(suite) -> [];
floats(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line F1 = 3.1414,
?line F2 = 3.1415,
?line F3 = 3.1416,
@@ -218,7 +218,7 @@ floats(Config) when is_list(Config) ->
binaries(suite) -> [];
binaries(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line Bin1 = term_to_binary({kalle, 146015, {kungsgatan, 23}}),
?line Bin2 = term_to_binary(sune),
?line Bin3 = list_to_binary("sune"),
@@ -237,7 +237,7 @@ binaries(Config) when is_list(Config) ->
strings(suite) -> [];
strings(Config) when is_list(Config) ->
- ?line P = start_matcher(),
+ ?line P = start_matcher(Config),
?line S1 = "string",
?line S2 = "streng",
@@ -254,7 +254,7 @@ strings(Config) when is_list(Config) ->
bind(suite) -> [];
bind(Config) when is_list(Config) ->
- ?line P = start_bind(),
+ ?line P = start_bind(Config),
?line S = "[X,Y,Z]",
?line L1 = [301,302,302],
?line L2 = [65,66,67],
@@ -265,7 +265,7 @@ bind(Config) when is_list(Config) ->
?line runner:finish(P),
ok.
-start_bind() ->
+start_bind(Config) ->
runner:start(?erl_match_bind).
bind_ok(Port, Bind, Term) ->
@@ -287,7 +287,7 @@ erl_bind(Port, Pattern, Term) ->
-start_matcher() ->
+start_matcher(Config) ->
runner:start(?erl_match_server).
eq(Port, Pattern, Term) ->
diff --git a/lib/erl_interface/vsn.mk b/lib/erl_interface/vsn.mk
index 2c402bba6c..0e249d2483 100644
--- a/lib/erl_interface/vsn.mk
+++ b/lib/erl_interface/vsn.mk
@@ -1 +1 @@
-EI_VSN = 3.7.6
+EI_VSN = 3.7.7
diff --git a/lib/et/doc/src/Makefile b/lib/et/doc/src/Makefile
index 6bb8164e91..facd335449 100644
--- a/lib/et/doc/src/Makefile
+++ b/lib/et/doc/src/Makefile
@@ -97,14 +97,14 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/et/doc/src/et_intro.xml b/lib/et/doc/src/et_intro.xml
index 0c5fb14d55..60da289721 100644
--- a/lib/et/doc/src/et_intro.xml
+++ b/lib/et/doc/src/et_intro.xml
@@ -40,8 +40,8 @@
ports or files.</p>
<section>
- <title>Scope and Purpose</title>'
-
+ <title>Scope and Purpose</title>
+
<p>This manual describes the <c>Event Tracer (ET)</c> application,
as a component of the Erlang/Open Telecom Platform development
environment. It is assumed that the reader is familiar with the
diff --git a/lib/et/doc/src/notes.xml b/lib/et/doc/src/notes.xml
index acc6120fcd..42790e0cdf 100644
--- a/lib/et/doc/src/notes.xml
+++ b/lib/et/doc/src/notes.xml
@@ -36,6 +36,26 @@
one section in this document. The title of each section is the
version number of <c>Event Tracer (ET)</c>.</p>
+<section><title>ET 1.4.4.1</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>ET 1.4.4</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/et/examples/Makefile b/lib/et/examples/Makefile
index 67a6536fdf..190d5e2d6a 100644
--- a/lib/et/examples/Makefile
+++ b/lib/et/examples/Makefile
@@ -73,8 +73,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/et/src/Makefile b/lib/et/src/Makefile
index bb6632ee91..7693571c5c 100644
--- a/lib/et/src/Makefile
+++ b/lib/et/src/Makefile
@@ -104,14 +104,14 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/et/test/Makefile b/lib/et/test/Makefile
index e10a2a1587..7b4db7b0c3 100644
--- a/lib/et/test/Makefile
+++ b/lib/et/test/Makefile
@@ -70,12 +70,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) et.spec et.cover $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_SCRIPT) ett $(RELSYSDIR)
- $(INSTALL_DATA) $(INSTALL_PROGS) $(RELSYSDIR)
-# chmod -R u+w $(RELSYSDIR)
-# @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) et.spec et.cover $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_SCRIPT) ett "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(INSTALL_PROGS) "$(RELSYSDIR)"
+# chmod -R u+w "$(RELSYSDIR)"
+# @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/et/vsn.mk b/lib/et/vsn.mk
index 239a72ad73..090d43d52f 100644
--- a/lib/et/vsn.mk
+++ b/lib/et/vsn.mk
@@ -1 +1 @@
-ET_VSN = 1.4.4
+ET_VSN = 1.4.4.1
diff --git a/lib/eunit/doc/src/Makefile b/lib/eunit/doc/src/Makefile
index 2cdc579275..cbcd4c1507 100644
--- a/lib/eunit/doc/src/Makefile
+++ b/lib/eunit/doc/src/Makefile
@@ -157,14 +157,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/eunit/examples/Makefile b/lib/eunit/examples/Makefile
index 48ec2ebf2b..cfa0a7a645 100644
--- a/lib/eunit/examples/Makefile
+++ b/lib/eunit/examples/Makefile
@@ -49,8 +49,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(EXAMPLE_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/eunit/src/Makefile b/lib/eunit/src/Makefile
index bec2fdbe0b..0a2e71cf7b 100644
--- a/lib/eunit/src/Makefile
+++ b/lib/eunit/src/Makefile
@@ -28,6 +28,9 @@ ERL_COMPILE_FLAGS += -pa $(EBIN) -I$(INCLUDE) +warn_unused_vars +nowarn_shadow_v
PARSE_TRANSFORM = eunit_autoexport.erl
+BEHAVIOUR_SOURCES= \
+ eunit_listener.erl
+
SOURCES= \
eunit_striptests.erl \
eunit.erl \
@@ -40,13 +43,16 @@ SOURCES= \
eunit_data.erl \
eunit_tty.erl \
eunit_surefire.erl \
- eunit_listener.erl
INCLUDE_FILES = eunit.hrl
PARSE_TRANSFORM_BIN = $(PARSE_TRANSFORM:%.erl=$(EBIN)/%.$(EMULATOR))
-OBJECTS=$(SOURCES:%.erl=$(EBIN)/%.$(EMULATOR)) $(APP_TARGET) $(APPUP_TARGET)
+TARGET_FILES= $(SOURCES:%.erl=$(EBIN)/%.$(EMULATOR))
+
+BEHAVIOUR_TARGET_FILES= $(BEHAVIOUR_SOURCES:%.erl=$(EBIN)/%.$(EMULATOR))
+
+OBJECTS= $(TARGET_FILES) $(BEHAVIOUR_TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
INCLUDE_DELIVERABLES = $(INCLUDE_FILES:%=$(INCLUDE)/%)
@@ -62,6 +68,8 @@ APPUP_TARGET= $(EBIN)/$(APPUP_FILE)
# Targets
# ----------------------------------------------------
+$(TARGET_FILES): $(BEHAVIOUR_TARGET_FILES)
+
debug opt: $(PARSE_TRANSFORM_BIN) $(OBJECTS)
docs:
@@ -107,12 +115,12 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(PARSE_TRANSFORM_BIN) $(OBJECTS) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(PARSE_TRANSFORM) $(SOURCES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(INCLUDE_DELIVERABLES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(PARSE_TRANSFORM_BIN) $(OBJECTS) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(PARSE_TRANSFORM) $(SOURCES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(INCLUDE_DELIVERABLES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/eunit/test/Makefile b/lib/eunit/test/Makefile
index a2d276f619..1586dd8857 100644
--- a/lib/eunit/test/Makefile
+++ b/lib/eunit/test/Makefile
@@ -74,9 +74,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) eunit.spec $(EMAKEFILE) \
$(COVERFILE) $(ERL_FILES) \
- $(RELSYSDIR)
+ "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/gs/contribs/bonk/Makefile b/lib/gs/contribs/bonk/Makefile
index be096824dd..dc92149784 100644
--- a/lib/gs/contribs/bonk/Makefile
+++ b/lib/gs/contribs/bonk/Makefile
@@ -94,14 +94,14 @@ $(EBIN)/$(TOOLNAME).tool: $(TOOLNAME).tool
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/bonk/bitmaps
- $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) $(RELSYSDIR)/bonk/bitmaps
- $(INSTALL_DIR) $(RELSYSDIR)/bonk/sounds
- $(INSTALL_DATA) $(SOUNDS) $(RELSYSDIR)/bonk/sounds
- $(INSTALL_DIR) $(RELSYSDIR)/bonk
- $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) $(RELSYSDIR)/bonk
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/bonk/bitmaps"
+ $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) "$(RELSYSDIR)/bonk/bitmaps"
+ $(INSTALL_DIR) "$(RELSYSDIR)/bonk/sounds"
+ $(INSTALL_DATA) $(SOUNDS) "$(RELSYSDIR)/bonk/sounds"
+ $(INSTALL_DIR) "$(RELSYSDIR)/bonk"
+ $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) "$(RELSYSDIR)/bonk"
release_docs_spec:
diff --git a/lib/gs/contribs/cols/Makefile b/lib/gs/contribs/cols/Makefile
index 75ca75ffc0..4ce4204c92 100644
--- a/lib/gs/contribs/cols/Makefile
+++ b/lib/gs/contribs/cols/Makefile
@@ -91,12 +91,12 @@ $(EBIN)/help.gif: help.gif
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/cols/bitmaps
- $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) $(RELSYSDIR)/cols/bitmaps
- $(INSTALL_DIR) $(RELSYSDIR)/cols
- $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) $(RELSYSDIR)/cols
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/cols/bitmaps"
+ $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) "$(RELSYSDIR)/cols/bitmaps"
+ $(INSTALL_DIR) "$(RELSYSDIR)/cols"
+ $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) "$(RELSYSDIR)/cols"
release_docs_spec:
diff --git a/lib/gs/contribs/mandel/Makefile b/lib/gs/contribs/mandel/Makefile
index 61a7a612e0..451ece2c8f 100644
--- a/lib/gs/contribs/mandel/Makefile
+++ b/lib/gs/contribs/mandel/Makefile
@@ -90,11 +90,11 @@ $(EBIN)/help.gif: help.gif
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/mandel/bitmaps
- $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) $(RELSYSDIR)/mandel/bitmaps
- $(INSTALL_DIR) $(RELSYSDIR)/mandel
- $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) $(RELSYSDIR)/mandel
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/mandel/bitmaps"
+ $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) "$(RELSYSDIR)/mandel/bitmaps"
+ $(INSTALL_DIR) "$(RELSYSDIR)/mandel"
+ $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) "$(RELSYSDIR)/mandel"
release_docs_spec:
diff --git a/lib/gs/contribs/othello/Makefile b/lib/gs/contribs/othello/Makefile
index b81b35fb55..5f09f2ed13 100644
--- a/lib/gs/contribs/othello/Makefile
+++ b/lib/gs/contribs/othello/Makefile
@@ -89,12 +89,12 @@ $(EBIN)/$(TOOLNAME).tool: $(TOOLNAME).tool
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/othello
- $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) $(RELSYSDIR)/othello
- $(INSTALL_DIR) $(RELSYSDIR)/othello/priv
- $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) $(RELSYSDIR)/othello/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/othello"
+ $(INSTALL_DATA) $(ERL_FILES) $(EXTRA_FILES) "$(RELSYSDIR)/othello"
+ $(INSTALL_DIR) "$(RELSYSDIR)/othello/priv"
+ $(INSTALL_DATA) $(BITMAPS) $(TOOLBOX_FILES) "$(RELSYSDIR)/othello/priv"
release_docs_spec:
diff --git a/lib/gs/doc/src/Makefile b/lib/gs/doc/src/Makefile
index 192dd67a52..14204c52fc 100644
--- a/lib/gs/doc/src/Makefile
+++ b/lib/gs/doc/src/Makefile
@@ -144,13 +144,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- (/bin/cp -rf $(HTMLDIR) $(RELSYSDIR)/doc)
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ (/bin/cp -rf $(HTMLDIR) "$(RELSYSDIR)/doc")
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/gs/doc/src/notes.xml b/lib/gs/doc/src/notes.xml
index cd63104346..d1b74ecfb1 100644
--- a/lib/gs/doc/src/notes.xml
+++ b/lib/gs/doc/src/notes.xml
@@ -30,7 +30,27 @@
</header>
<p>This document describes the changes made to the GS application.</p>
- <section><title>GS 1.5.15</title>
+ <section><title>GS 1.5.15.1</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>GS 1.5.15</title>
<section><title>Improvements and New Features</title>
<list>
diff --git a/lib/gs/examples/Makefile b/lib/gs/examples/Makefile
index 10b166b207..d214cd2256 100644
--- a/lib/gs/examples/Makefile
+++ b/lib/gs/examples/Makefile
@@ -87,9 +87,9 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
release_docs_spec:
diff --git a/lib/gs/src/Makefile b/lib/gs/src/Makefile
index 43b530295b..a9904161a4 100644
--- a/lib/gs/src/Makefile
+++ b/lib/gs/src/Makefile
@@ -107,13 +107,13 @@ $(GSTK_GENERIC_TARGET): gstk_generic.hrl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
$(INSTALL_DATA) $(APP_SRC) $(ERL_FILES) $(HRL_FILES) $(GEN_HRL_FILES) \
- $(GSTK_GENERIC) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bitmap
- $(INSTALL_DATA) $(IMAGES) $(RELSYSDIR)/priv/bitmap
+ $(GSTK_GENERIC) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bitmap"
+ $(INSTALL_DATA) $(IMAGES) "$(RELSYSDIR)/priv/bitmap"
release_docs_spec:
diff --git a/lib/gs/src/gstk_generic.erl b/lib/gs/src/gstk_generic.erl
index 10cb890013..9b0efd07c1 100644
--- a/lib/gs/src/gstk_generic.erl
+++ b/lib/gs/src/gstk_generic.erl
@@ -323,7 +323,7 @@ handle_external_opt_call([Opt|Options],Gstkid,TkW,DB,ExtraArg,ExtRes,S,P,C) ->
end.
handle_external_read(Res) ->
- case Res of
+ _ = case Res of
{bad_result,{Objtype,Reason,Option}} ->
{error,{Objtype,Reason,Option}};
_ -> ok
diff --git a/lib/gs/tcl/Makefile.in b/lib/gs/tcl/Makefile.in
index dce34a4baa..0bccb60c7b 100644
--- a/lib/gs/tcl/Makefile.in
+++ b/lib/gs/tcl/Makefile.in
@@ -74,10 +74,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(TCL_FILES) $(EXTRA_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(TCL_FILES) $(EXTRA_FILES) "$(RELSYSDIR)/priv"
ifneq ($(TCL_TAR),)
- gzip -dc $(TCL_TAR) | (cd $(RELSYSDIR)/priv && tar -xf -)
+ gzip -dc $(TCL_TAR) | (cd "$(RELSYSDIR)/priv" && tar -xf -)
endif
release_docs_spec:
diff --git a/lib/gs/vsn.mk b/lib/gs/vsn.mk
index 41a2561809..48249cb3d0 100644
--- a/lib/gs/vsn.mk
+++ b/lib/gs/vsn.mk
@@ -1,2 +1,2 @@
-GS_VSN = 1.5.15
+GS_VSN = 1.5.15.1
diff --git a/lib/hipe/amd64/Makefile b/lib/hipe/amd64/Makefile
index 15291e9bbe..50cd024d72 100644
--- a/lib/hipe/amd64/Makefile
+++ b/lib/hipe/amd64/Makefile
@@ -105,8 +105,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/arm/Makefile b/lib/hipe/arm/Makefile
index a64f133679..651b82f1ed 100644
--- a/lib/hipe/arm/Makefile
+++ b/lib/hipe/arm/Makefile
@@ -106,8 +106,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/cerl/Makefile b/lib/hipe/cerl/Makefile
index 14e68f5233..506e993ff4 100644
--- a/lib/hipe/cerl/Makefile
+++ b/lib/hipe/cerl/Makefile
@@ -42,7 +42,7 @@ RELSYSDIR = $(RELEASE_PATH)/lib/hipe-$(VSN)
# ----------------------------------------------------
# Target Specs
# ----------------------------------------------------
-MODULES = cerl_cconv cerl_closurean cerl_hipeify cerl_hybrid_transform \
+MODULES = cerl_cconv cerl_closurean cerl_hipeify \
cerl_lib cerl_messagean cerl_pmatch cerl_prettypr cerl_to_icode \
cerl_typean erl_bif_types erl_types
@@ -100,10 +100,10 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/cerl
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/cerl
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/cerl"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/cerl"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/cerl/cerl_hybrid_transform.erl b/lib/hipe/cerl/cerl_hybrid_transform.erl
deleted file mode 100644
index b248b0ccd0..0000000000
--- a/lib/hipe/cerl/cerl_hybrid_transform.erl
+++ /dev/null
@@ -1,153 +0,0 @@
-%%
-%% %CopyrightBegin%
-%%
-%% Copyright Ericsson AB 2004-2009. 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
-%% Erlang Public License along with this software. If not, it can be
-%% retrieved online at http://www.erlang.org/.
-%%
-%% Software distributed under the License is distributed on an "AS IS"
-%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
-%% the License for the specific language governing rights and limitations
-%% under the License.
-%%
-%% %CopyrightEnd%
-%%
-
--module(cerl_hybrid_transform).
-
-%% Use compile option `{core_transform, cerl_hybrid_transform}' to
-%% insert this as a compilation pass.
-
--export([transform/2, core_transform/2]).
-
--spec core_transform(cerl:cerl(), [term()]) -> cerl:cerl().
-
-core_transform(Code, Opts) ->
- cerl:to_records(transform(cerl:from_records(Code), Opts)).
-
--spec transform(cerl:cerl(), [term()]) -> cerl:cerl().
-
-transform(Code, _Opts) ->
- Code0 = cerl_trees:map(fun unfold_literal/1, Code),
- {Code1, _} = cerl_trees:label(Code0),
- io:fwrite("Running hybrid heap analysis..."),
- {T1,_} = statistics(runtime),
- {Code2, _, Vars} = cerl_messagean:annotate(Code1),
- {T2,_} = statistics(runtime),
- io:fwrite("(~w ms), transform...", [T2 - T1]),
- Code3 = rewrite(Code2, Vars),
- io:fwrite("done.\n"),
- cerl_trees:map(fun fold_literal/1, Code3).
-
-unfold_literal(T) ->
- cerl:unfold_literal(T).
-
-fold_literal(T) ->
- cerl:fold_literal(T).
-
-%% If escape-annotated:
-%% {...} => hybrid:tuple([...])
-%% [H | T] => hybrid:cons(H, T)
-%%
-%% Wrapper for args to hybrid:cons/hybrid:tuple that may need copying:
-%% hybrid:copy(A)
-
-rewrite(Node, Vars) ->
- case cerl:type(Node) of
- tuple ->
- Es = rewrite_list(cerl:tuple_es(Node), Vars),
- case is_escaping(Node) of
- false ->
- cerl:update_c_tuple(Node, Es);
- true ->
- Es1 = wrap(Es, Node, Vars),
- cerl:update_c_call(Node,
- cerl:abstract(hybrid),
- cerl:abstract(tuple),
- [cerl:make_list(Es1)])
-%%% cerl:update_c_call(Node, cerl:abstract(hybrid),
-%%% cerl:abstract(tuple), Es1)
- end;
- cons ->
- H = rewrite(cerl:cons_hd(Node), Vars),
- T = rewrite(cerl:cons_tl(Node), Vars),
- case is_escaping(Node) of
- false ->
- cerl:update_c_cons(Node, H, T);
- true ->
- Es = wrap([H, T], Node, Vars),
- cerl:update_c_call(Node,
- cerl:abstract(hybrid),
- cerl:abstract(cons),
- Es)
- end;
-%%% call ->
-%%% M = rewrite(cerl:call_module(Node)),
-%%% F = rewrite(cerl:call_name(Node)),
-%%% As = rewrite_list(cerl:call_args(Node)),
-%%% case cerl:is_c_atom(M) andalso cerl:is_c_atom(F) of
-%%% true ->
-%%% case {cerl:atom_val(M), cerl:atom_val(F), length(As)} of
-%%% {erlang, '!', 2} ->
-%%% cerl:update_c_call(Node,
-%%% cerl:abstract(hipe_bifs),
-%%% cerl:abstract(send),
-%%% [cerl:make_list(As)]);
-%%% _ ->
-%%% cerl:update_c_call(Node, M, F, As)
-%%% end;
-%%% false ->
-%%% cerl:update_c_call(Node, M, F, As)
-%%% end;
- clause ->
- B = rewrite(cerl:clause_body(Node), Vars),
- cerl:update_c_clause(Node, cerl:clause_pats(Node),
- cerl:clause_guard(Node), B);
- primop ->
- case cerl:atom_val(cerl:primop_name(Node)) of
- match_fail ->
- Node;
- _ ->
- As = rewrite_list(cerl:primop_args(Node), Vars),
- cerl:update_c_primop(Node, cerl:primop_name(Node), As)
- end;
- _T ->
- case cerl:subtrees(Node) of
- [] ->
- Node;
- Gs ->
- cerl:update_tree(Node, [rewrite_list(Ns, Vars)
- || Ns <- Gs])
- end
- end.
-
-rewrite_list([N | Ns], Vars) ->
- [rewrite(N, Vars) | rewrite_list(Ns, Vars)];
-rewrite_list([], _) ->
- [].
-
-is_escaping(T) ->
- lists:member(escapes, cerl:get_ann(T)).
-
-wrap(Es, Node, Vars) ->
- L = cerl_trees:get_label(Node),
- Xs = dict:fetch(L, Vars),
- wrap(Es, Xs).
-
-wrap([E | Es], [{S, _} | Xs]) ->
- case ordsets:is_element(unsafe, S) of
-%% case cerl:type(E) =/= literal of
- true ->
- [cerl:c_call(cerl:abstract(hybrid),
- cerl:abstract(copy),
- [E])
- | wrap(Es, Xs)];
- false ->
- [E | wrap(Es, Xs)]
- end;
-wrap([], _) ->
- [].
diff --git a/lib/hipe/cerl/erl_bif_types.erl b/lib/hipe/cerl/erl_bif_types.erl
index 0c2e846010..1ef73da1be 100644
--- a/lib/hipe/cerl/erl_bif_types.erl
+++ b/lib/hipe/cerl/erl_bif_types.erl
@@ -1186,6 +1186,7 @@ type(erlang, port_info, 2, Xs) ->
['links'] -> t_tuple([Item, t_list(t_pid())]);
['name'] -> t_tuple([Item, t_string()]);
['output'] -> t_tuple([Item, t_integer()]);
+ ['os_pid'] -> t_tuple([Item, t_sup(t_non_neg_integer(),t_atom('undefined'))]);
['registered_name'] -> t_tuple([Item, t_atom()]);
List when is_list(List) ->
t_tuple([t_sup([t_atom(A) || A <- List]),
@@ -1268,7 +1269,6 @@ type(erlang, process_info, 2, Xs) ->
['links'] -> t_tuple([InfoItem, t_list(t_pid())]);
['memory'] ->
t_tuple([InfoItem, t_non_neg_integer()]);
- ['message_binary'] -> t_tuple([InfoItem, t_list()]);
['message_queue_len'] ->
t_tuple([InfoItem, t_non_neg_integer()]);
['messages'] -> t_tuple([InfoItem, t_list()]);
@@ -1593,14 +1593,10 @@ type(erlang, system_info, 1, Xs) ->
t_tuple([t_atom('fullsweep_after'), t_non_neg_integer()]);
['garbage_collection'] ->
t_list();
- ['global_heaps_size'] ->
- t_non_neg_integer();
['heap_sizes'] ->
t_list(t_integer());
['heap_type'] ->
- t_sup([t_atom('private'),
- t_atom('shared'),
- t_atom('hybrid')]);
+ t_atom('private');
['hipe_architecture'] ->
t_atoms(['amd64', 'arm', 'powerpc', 'ppc64',
'undefined', 'ultrasparc', 'x86']);
@@ -3789,7 +3785,7 @@ arg_types(erlang, port_info, 1) ->
arg_types(erlang, port_info, 2) ->
[t_sup(t_port(), t_atom()),
t_atoms(['registered_name', 'id', 'connected',
- 'links', 'name', 'input', 'output'])];
+ 'links', 'name', 'input', 'output', 'os_pid'])];
arg_types(erlang, port_to_list, 1) ->
[t_port()];
arg_types(erlang, ports, 0) ->
@@ -4742,7 +4738,6 @@ t_pinfo_item() ->
t_atom('last_calls'),
t_atom('links'),
t_atom('memory'),
- t_atom('message_binary'), % for hybrid heap only
t_atom('message_queue_len'),
t_atom('messages'),
t_atom('monitored_by'),
diff --git a/lib/hipe/cerl/erl_types.erl b/lib/hipe/cerl/erl_types.erl
index ceec31742e..1789fc79fa 100644
--- a/lib/hipe/cerl/erl_types.erl
+++ b/lib/hipe/cerl/erl_types.erl
@@ -2555,8 +2555,8 @@ t_subst_dict(?list(Contents, Termination, Size), Dict) ->
?nil -> ?list(NewContents, ?nil, Size);
?any -> ?list(NewContents, ?any, Size);
Other ->
- ?list(NewContents, NewTermination, _) = t_cons(NewContents, Other),
- ?list(NewContents, NewTermination, Size)
+ ?list(NewContents2, NewTermination, _) = t_cons(NewContents, Other),
+ ?list(NewContents2, NewTermination, Size)
end
end;
t_subst_dict(?function(Domain, Range), Dict) ->
@@ -2597,8 +2597,8 @@ t_subst_aux(?list(Contents, Termination, Size), VarMap) ->
?nil -> ?list(NewContents, ?nil, Size);
?any -> ?list(NewContents, ?any, Size);
Other ->
- ?list(NewContents, NewTermination, _) = t_cons(NewContents, Other),
- ?list(NewContents, NewTermination, Size)
+ ?list(NewContents2, NewTermination, _) = t_cons(NewContents, Other),
+ ?list(NewContents2, NewTermination, Size)
end
end;
t_subst_aux(?function(Domain, Range), VarMap) ->
@@ -3186,8 +3186,8 @@ t_abstract_records(?list(Contents, Termination, Size), RecDict) ->
?nil -> ?list(NewContents, ?nil, Size);
?any -> ?list(NewContents, ?any, Size);
Other ->
- ?list(NewContents, NewTermination, _) = t_cons(NewContents, Other),
- ?list(NewContents, NewTermination, Size)
+ ?list(NewContents2, NewTermination, _) = t_cons(NewContents, Other),
+ ?list(NewContents2, NewTermination, Size)
end
end;
t_abstract_records(?function(Domain, Range), RecDict) ->
diff --git a/lib/hipe/doc/src/Makefile b/lib/hipe/doc/src/Makefile
index a9cd583ff4..fbfd4ca327 100644
--- a/lib/hipe/doc/src/Makefile
+++ b/lib/hipe/doc/src/Makefile
@@ -106,12 +106,12 @@ realclean: clean
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
release_spec:
diff --git a/lib/hipe/doc/src/notes.xml b/lib/hipe/doc/src/notes.xml
index 3f28cf9959..ed8cf0b8d3 100644
--- a/lib/hipe/doc/src/notes.xml
+++ b/lib/hipe/doc/src/notes.xml
@@ -30,6 +30,52 @@
</header>
<p>This document describes the changes made to HiPE.</p>
+<section><title>Hipe 3.9.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ References to <c>is_constant/1</c> (which was removed in
+ the R12 release) has been removed from documentation and
+ code.</p>
+ <p>
+ Own Id: OTP-6454 Aux Id: seq10407 </p>
+ </item>
+ <item>
+ <p>
+ Fixed a discrepancy in compile_info</p>
+ <p>
+ The BEAM disassembler used the atom 'none' to signify the
+ absence of a compile_info chunk in a .beam file. This
+ clashed with the type declaration of the compile_info
+ field of a #beam_file{} record as containing a list. Now
+ [] signifies the absence of this chunk. This simplifies
+ the code and avoids a dialyzer warning.</p>
+ <p>
+ Own Id: OTP-9917</p>
+ </item>
+ <item>
+ <p>
+ Make dialyzer recognize the process_flag option sensitive
+ add missing specs to documentation (Thanks to Tobias
+ Schlager)</p>
+ <p>
+ Own Id: OTP-9923</p>
+ </item>
+ <item>
+ <p>
+ Remove hipe_ceach from hipe.app.src to fix
+ reltool-generated release startup. (Thanks to Tim
+ Stewart)</p>
+ <p>
+ Own Id: OTP-9939</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Hipe 3.9</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/hipe/flow/Makefile b/lib/hipe/flow/Makefile
index 1a531fdfe5..75e156b542 100644
--- a/lib/hipe/flow/Makefile
+++ b/lib/hipe/flow/Makefile
@@ -100,10 +100,10 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/flow
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(INC_FILES) $(RELSYSDIR)/flow
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/flow"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(INC_FILES) "$(RELSYSDIR)/flow"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/icode/Makefile b/lib/hipe/icode/Makefile
index 0d940d4b28..0f2d6db39b 100644
--- a/lib/hipe/icode/Makefile
+++ b/lib/hipe/icode/Makefile
@@ -118,10 +118,10 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/icode
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/icode
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/icode"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/icode"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/main/Makefile b/lib/hipe/main/Makefile
index fc8923db6c..673431a175 100644
--- a/lib/hipe/main/Makefile
+++ b/lib/hipe/main/Makefile
@@ -115,10 +115,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DATA) ../vsn.mk $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/main
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/main
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DATA) ../vsn.mk "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/main"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/main"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/main/hipe.app.src b/lib/hipe/main/hipe.app.src
index d38b9ea7b1..7db4db8a57 100644
--- a/lib/hipe/main/hipe.app.src
+++ b/lib/hipe/main/hipe.app.src
@@ -24,7 +24,6 @@
{modules, [cerl_cconv,
cerl_closurean,
cerl_hipeify,
- cerl_hybrid_transform,
cerl_lib,
cerl_messagean,
cerl_pmatch,
diff --git a/lib/hipe/main/hipe.erl b/lib/hipe/main/hipe.erl
index c73db872ac..b2789978a4 100644
--- a/lib/hipe/main/hipe.erl
+++ b/lib/hipe/main/hipe.erl
@@ -482,12 +482,7 @@ compile(Name, File, Opts0) when is_atom(Name) ->
compile_core(Name, Core0, File, Opts) ->
Core = cerl:from_records(Core0),
- Core1 = case (erlang:system_info(heap_type) =:= hybrid)
- andalso proplists:get_bool(hybrid, Opts) of
- true -> cerl_hybrid_transform:transform(Core, Opts);
- false -> Core
- end,
- compile(Name, Core1, File, Opts).
+ compile(Name, Core, File, Opts).
%% @spec compile(Name, Core, File, options()) ->
%% {ok, {Target, Binary}} | {error, Reason}
diff --git a/lib/hipe/misc/Makefile b/lib/hipe/misc/Makefile
index 98a69d62c7..1204ab7c0b 100644
--- a/lib/hipe/misc/Makefile
+++ b/lib/hipe/misc/Makefile
@@ -100,10 +100,10 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/misc
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/misc
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/misc"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/misc"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/opt/Makefile b/lib/hipe/opt/Makefile
index 426afd8052..a21c543574 100644
--- a/lib/hipe/opt/Makefile
+++ b/lib/hipe/opt/Makefile
@@ -97,8 +97,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/ppc/Makefile b/lib/hipe/ppc/Makefile
index c4b0c3ba9d..8bd2a8226c 100644
--- a/lib/hipe/ppc/Makefile
+++ b/lib/hipe/ppc/Makefile
@@ -108,8 +108,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/regalloc/Makefile b/lib/hipe/regalloc/Makefile
index d33f641640..d4be79ea85 100644
--- a/lib/hipe/regalloc/Makefile
+++ b/lib/hipe/regalloc/Makefile
@@ -112,8 +112,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/rtl/Makefile b/lib/hipe/rtl/Makefile
index 30026831b7..426d1bd3ee 100644
--- a/lib/hipe/rtl/Makefile
+++ b/lib/hipe/rtl/Makefile
@@ -103,10 +103,10 @@ realclean: clean
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/rtl
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/rtl
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/rtl"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/rtl"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/sparc/Makefile b/lib/hipe/sparc/Makefile
index e9e9d54e0c..eb40117691 100644
--- a/lib/hipe/sparc/Makefile
+++ b/lib/hipe/sparc/Makefile
@@ -108,8 +108,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/tools/Makefile b/lib/hipe/tools/Makefile
index f90d3c9f70..6761f11b01 100644
--- a/lib/hipe/tools/Makefile
+++ b/lib/hipe/tools/Makefile
@@ -96,8 +96,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/util/Makefile b/lib/hipe/util/Makefile
index 2f17eee7f3..a5ee232057 100644
--- a/lib/hipe/util/Makefile
+++ b/lib/hipe/util/Makefile
@@ -103,10 +103,10 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/util
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/util
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/util"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/util"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/hipe/vsn.mk b/lib/hipe/vsn.mk
index 347a0336cd..e296997466 100644
--- a/lib/hipe/vsn.mk
+++ b/lib/hipe/vsn.mk
@@ -1 +1 @@
-HIPE_VSN = 3.9
+HIPE_VSN = 3.9.1
diff --git a/lib/hipe/x86/Makefile b/lib/hipe/x86/Makefile
index f92e7eeec1..3602949944 100644
--- a/lib/hipe/x86/Makefile
+++ b/lib/hipe/x86/Makefile
@@ -116,8 +116,8 @@ $(DOCS)/%.html:%.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/ic/c_src/Makefile.in b/lib/ic/c_src/Makefile.in
index 5e034c47c6..d8b8c85a8e 100644
--- a/lib/ic/c_src/Makefile.in
+++ b/lib/ic/c_src/Makefile.in
@@ -140,12 +140,12 @@ $(OBJDIR)/%.o: %.c
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/c_src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/priv/lib
- $(INSTALL_DATA) ic.c ic_tmo.c $(RELSYSDIR)/c_src
- $(INSTALL_DATA) $(IDL_FILES) $(H_FILES) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(LIBRARY) $(RELSYSDIR)/priv/lib
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_DATA) ic.c ic_tmo.c "$(RELSYSDIR)/c_src"
+ $(INSTALL_DATA) $(IDL_FILES) $(H_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(LIBRARY) "$(RELSYSDIR)/priv/lib"
release_docs_spec:
diff --git a/lib/ic/doc/src/Makefile b/lib/ic/doc/src/Makefile
index 208f16e441..0ee242b234 100644
--- a/lib/ic/doc/src/Makefile
+++ b/lib/ic/doc/src/Makefile
@@ -220,12 +220,12 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- (/bin/cp -rf $(HTMLDIR) $(RELSYSDIR)/doc)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ (/bin/cp -rf $(HTMLDIR) "$(RELSYSDIR)/doc")
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/ic/doc/src/notes.xml b/lib/ic/doc/src/notes.xml
index 6329bf1fb5..eac932fc06 100644
--- a/lib/ic/doc/src/notes.xml
+++ b/lib/ic/doc/src/notes.xml
@@ -30,7 +30,23 @@
<file>notes.xml</file>
</header>
- <section><title>IC 4.2.29</title>
+ <section><title>IC 4.2.30</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ Add generation of Erlang callback functions to generated
+ Erlang source code to avoid compiler warnings.</p>
+ <p>
+ Own Id: OTP-9998</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>IC 4.2.29</title>
<section><title>Improvements and New Features</title>
<list>
diff --git a/lib/ic/examples/pre_post_condition/Makefile b/lib/ic/examples/pre_post_condition/Makefile
index 8f85babb1a..8ae37394ed 100644
--- a/lib/ic/examples/pre_post_condition/Makefile
+++ b/lib/ic/examples/pre_post_condition/Makefile
@@ -124,8 +124,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/pre_post_condition
- $(INSTALL_DATA) $(ERL_FILES) $(IDL_FILES) $(TXT_FILES) $(RELSYSDIR)/examples/pre_post_condition
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/pre_post_condition"
+ $(INSTALL_DATA) $(ERL_FILES) $(IDL_FILES) $(TXT_FILES) "$(RELSYSDIR)/examples/pre_post_condition"
release_docs_spec:
diff --git a/lib/ic/java_src/com/ericsson/otp/ic/Makefile b/lib/ic/java_src/com/ericsson/otp/ic/Makefile
index f730749ccb..1b14d4430f 100644
--- a/lib/ic/java_src/com/ericsson/otp/ic/Makefile
+++ b/lib/ic/java_src/com/ericsson/otp/ic/Makefile
@@ -109,10 +109,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/java_src/com/ericsson/otp/ic
- $(INSTALL_DATA) $(JAVA_FILES) $(RELSYSDIR)/java_src/com/ericsson/otp/ic
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(JAVA_DEST_ROOT)$(JARFILE) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/java_src/com/ericsson/otp/ic"
+ $(INSTALL_DATA) $(JAVA_FILES) "$(RELSYSDIR)/java_src/com/ericsson/otp/ic"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(JAVA_DEST_ROOT)$(JARFILE) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/ic/src/Makefile b/lib/ic/src/Makefile
index 5dac304e32..c830ebec95 100644
--- a/lib/ic/src/Makefile
+++ b/lib/ic/src/Makefile
@@ -196,23 +196,23 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DIR) $(RELSYSDIR)/examples/c-client
- $(INSTALL_DATA) $(CCL_EX_FILES) $(RELSYSDIR)/examples/c-client
- $(INSTALL_DIR) $(RELSYSDIR)/examples/c-server
- $(INSTALL_DATA) $(CSRV_EX_FILES) $(RELSYSDIR)/examples/c-server
- $(INSTALL_DIR) $(RELSYSDIR)/examples/erl-plain
- $(INSTALL_DATA) $(EPL_EX_FILES) $(RELSYSDIR)/examples/erl-plain
- $(INSTALL_DIR) $(RELSYSDIR)/examples/erl-genserv
- $(INSTALL_DATA) $(ESRV_EX_FILES) $(RELSYSDIR)/examples/erl-genserv
- $(INSTALL_DIR) $(RELSYSDIR)/examples/java-client-server
- $(INSTALL_DATA) $(JAVA_EX_FILES) $(RELSYSDIR)/examples/java-client-server
- $(INSTALL_DIR) $(RELSYSDIR)/examples/all-against-all
- $(INSTALL_DATA) $(MIXED_EX_FILES) $(RELSYSDIR)/examples/all-against-all
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/c-client"
+ $(INSTALL_DATA) $(CCL_EX_FILES) "$(RELSYSDIR)/examples/c-client"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/c-server"
+ $(INSTALL_DATA) $(CSRV_EX_FILES) "$(RELSYSDIR)/examples/c-server"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/erl-plain"
+ $(INSTALL_DATA) $(EPL_EX_FILES) "$(RELSYSDIR)/examples/erl-plain"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/erl-genserv"
+ $(INSTALL_DATA) $(ESRV_EX_FILES) "$(RELSYSDIR)/examples/erl-genserv"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/java-client-server"
+ $(INSTALL_DATA) $(JAVA_EX_FILES) "$(RELSYSDIR)/examples/java-client-server"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/all-against-all"
+ $(INSTALL_DATA) $(MIXED_EX_FILES) "$(RELSYSDIR)/examples/all-against-all"
release_docs_spec:
diff --git a/lib/ic/src/ic.erl b/lib/ic/src/ic.erl
index 50fad921c4..bc7ec8ba91 100644
--- a/lib/ic/src/ic.erl
+++ b/lib/ic/src/ic.erl
@@ -250,7 +250,7 @@ make_erl_options(Opts) ->
Optimize = Opts#options.optimize,
PreProc =
lists:flatten(
- lists:map(fun(D) -> io_lib:format("-I~s ", [ic_util:to_list(D)]) end,
+ lists:map(fun(D) -> io_lib:format("-I\"~s\" ", [ic_util:to_list(D)]) end,
Includes1)++
lists:map(
fun ({Name, Value}) ->
diff --git a/lib/ic/src/ic_pp.erl b/lib/ic/src/ic_pp.erl
index 8b53473caa..50eeeab48c 100644
--- a/lib/ic/src/ic_pp.erl
+++ b/lib/ic/src/ic_pp.erl
@@ -1894,23 +1894,37 @@ include_dir(Flags) when is_list(Flags)->
include_dir(_Flags) ->
[].
-include_dir(Flags,IncDir) ->
+include_dir(Flags,IncDirs) ->
case string:str(Flags,"-I") of
0 ->
- lists:reverse(IncDir);
+ lists:reverse(IncDirs);
X ->
- Rem2 = string:sub_string(Flags, X+2),
- Rem = string:strip(Rem2, left),
- Y = string:str(Rem," "),
- case string:str(Rem," ") of
- 0 ->
- lists:reverse([string:sub_string(Rem, Y+1)|IncDir]);
- Y ->
- include_dir(string:sub_string(Rem, Y+1),
- [string:sub_string(Rem,1,Y-1)|IncDir])
- end
+ {NewDir, RemainingFlags} =
+ gobble_inc_dir(string:sub_string(Flags, X+2),nq,[]),
+ include_dir(RemainingFlags, [NewDir|IncDirs])
end.
+% nq = not-quoted, q = quoted.
+% Possible strange scenarios:
+% /usr/test\ ing/
+% "/usr/test ing/"
+% /usr/test\"ing/
+% "/usr/test\"ing/"
+gobble_inc_dir([],nq,Acc) ->
+ % Only accept nq here, if we end up here in q mode the user has missed a "
+ {lists:reverse(Acc),[]};
+gobble_inc_dir([$\\,$"|R],Q,Acc) ->
+ gobble_inc_dir(R,Q,[$"|Acc]);
+gobble_inc_dir([$"|R],nq,Acc) ->
+ gobble_inc_dir(R,q,Acc);
+gobble_inc_dir([$"|R],q,Acc) ->
+ gobble_inc_dir(R,nq,Acc);
+gobble_inc_dir([$\\,$ |R],nq,Acc) ->
+ gobble_inc_dir(R,nq,[$ |Acc]);
+gobble_inc_dir([$ |R],nq,Acc) ->
+ {lists:reverse(Acc),R};
+gobble_inc_dir([C|R],Q,Acc) ->
+ gobble_inc_dir(R,Q,[C|Acc]).
%%===============================================================
@@ -1954,7 +1968,6 @@ find_inc_file2(FileName, [D|Rem]) ->
_ ->
D++"/"
end,
-
case catch file:read_file_info(Dir++FileName) of
{ok, _} ->
{ok, Dir++FileName};
diff --git a/lib/ic/test/Makefile b/lib/ic/test/Makefile
index 1d90a1bc17..65003d703b 100644
--- a/lib/ic/test/Makefile
+++ b/lib/ic/test/Makefile
@@ -239,39 +239,39 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/ic_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/ic_register_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/ic_pragma_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/ic_pp_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/ic_be_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/c_client_erl_server_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/c_client_erl_server_proto_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/c_client_erl_server_proto_tmo_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/erl_client_c_server_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/erl_client_c_server_proto_SUITE_data
- $(INSTALL_DIR) $(RELSYSDIR)/java_client_erl_server_SUITE_data
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ic_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ic_register_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ic_pragma_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ic_pp_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ic_be_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_client_erl_server_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_client_erl_server_proto_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_client_erl_server_proto_tmo_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/erl_client_c_server_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/erl_client_c_server_proto_SUITE_data"
+ $(INSTALL_DIR) "$(RELSYSDIR)/java_client_erl_server_SUITE_data"
$(INSTALL_DATA) $(IDL_FILES) ic.cover $(TEST_SPEC_FILE) $(ERL_FILES) \
- $(RELSYSDIR)
- $(INSTALL_DATA) $(COMPILER_TEST_FILES) $(RELSYSDIR)/ic_SUITE_data
+ "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(COMPILER_TEST_FILES) "$(RELSYSDIR)/ic_SUITE_data"
$(INSTALL_DATA) $(COMPILER_TEST_FILES2) \
- $(RELSYSDIR)/ic_register_SUITE_data
+ "$(RELSYSDIR)/ic_register_SUITE_data"
$(INSTALL_DATA) $(COMPILER_TEST_FILES3) \
- $(RELSYSDIR)/ic_pragma_SUITE_data
+ "$(RELSYSDIR)/ic_pragma_SUITE_data"
$(INSTALL_DATA) $(COMPILER_TEST_FILES4) \
- $(RELSYSDIR)/ic_be_SUITE_data
+ "$(RELSYSDIR)/ic_be_SUITE_data"
$(INSTALL_DATA) $(PREPROCESSOR_TEST_FILES) \
- $(RELSYSDIR)/ic_pp_SUITE_data
+ "$(RELSYSDIR)/ic_pp_SUITE_data"
$(INSTALL_DATA) $(C_CLIENT_ERL_SERVER_TEST_FILES) \
- $(RELSYSDIR)/c_client_erl_server_SUITE_data
+ "$(RELSYSDIR)/c_client_erl_server_SUITE_data"
$(INSTALL_DATA) $(C_CLIENT_ERL_SERVER_PROTO_TEST_FILES) \
- $(RELSYSDIR)/c_client_erl_server_proto_SUITE_data
+ "$(RELSYSDIR)/c_client_erl_server_proto_SUITE_data"
$(INSTALL_DATA) $(C_CLIENT_ERL_SERVER_PROTO_TMO_TEST_FILES) \
- $(RELSYSDIR)/c_client_erl_server_proto_tmo_SUITE_data
+ "$(RELSYSDIR)/c_client_erl_server_proto_tmo_SUITE_data"
$(INSTALL_DATA) $(ERL_CLIENT_C_SERVER_TEST_FILES) \
- $(RELSYSDIR)/erl_client_c_server_SUITE_data
+ "$(RELSYSDIR)/erl_client_c_server_SUITE_data"
$(INSTALL_DATA) $(ERL_CLIENT_C_SERVER_PROTO_TEST_FILES) \
- $(RELSYSDIR)/erl_client_c_server_proto_SUITE_data
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
+ "$(RELSYSDIR)/erl_client_c_server_proto_SUITE_data"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
$(INSTALL_DATA) $(JAVA_CLIENT_ERL_SERVER_TEST_FILES) \
- $(RELSYSDIR)/java_client_erl_server_SUITE_data
+ "$(RELSYSDIR)/java_client_erl_server_SUITE_data"
diff --git a/lib/ic/test/java_client_erl_server_SUITE.erl b/lib/ic/test/java_client_erl_server_SUITE.erl
index 407c3d2d44..d4523dc2ad 100644
--- a/lib/ic/test/java_client_erl_server_SUITE.erl
+++ b/lib/ic/test/java_client_erl_server_SUITE.erl
@@ -249,7 +249,7 @@ marshal_any_2(Config) when is_list(Config) ->
java(Java, Dir, ClassAndArgs) ->
- cmd(Java++" -classpath "++classpath(Dir)++" "++ClassAndArgs).
+ cmd(Java++" -classpath \""++classpath(Dir)++"\" "++ClassAndArgs).
java(Java, Dir, Class, Args) ->
java(Java, Dir, Class++" "++to_string(Args)).
diff --git a/lib/inets/doc/src/Makefile b/lib/inets/doc/src/Makefile
index b3a98fd6d5..1a8e1c7ca8 100644
--- a/lib/inets/doc/src/Makefile
+++ b/lib/inets/doc/src/Makefile
@@ -140,13 +140,13 @@ clean_man:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(HTMLDIR)/* $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(HTMLDIR)/* "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/inets/examples/httpd_load_test/Makefile b/lib/inets/examples/httpd_load_test/Makefile
index 1cc61ad8ae..de1b2a289f 100644
--- a/lib/inets/examples/httpd_load_test/Makefile
+++ b/lib/inets/examples/httpd_load_test/Makefile
@@ -34,7 +34,7 @@ VSN=$(INETS_VSN)
# Release directory specification
# ----------------------------------------------------
RELSYSDIR = $(RELEASE_PATH)/lib/inets-$(VSN)
-EXAMPLE_RELSYSDIR = $(RELSYSDIR)/examples
+EXAMPLE_RELSYSDIR = "$(RELSYSDIR)/examples"
HDLT_RELSYSDIR = $(EXAMPLE_RELSYSDIR)/httpd_load_test
diff --git a/lib/inets/examples/server_root/Makefile b/lib/inets/examples/server_root/Makefile
index d7a3231068..2230a7eafc 100644
--- a/lib/inets/examples/server_root/Makefile
+++ b/lib/inets/examples/server_root/Makefile
@@ -174,36 +174,36 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/auth
- $(INSTALL_DATA) $(AUTH_FILES) $(RELSYSDIR)/examples/server_root/auth
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/cgi-bin
- $(INSTALL_SCRIPT) $(CGI_FILES) $(RELSYSDIR)/examples/server_root/cgi-bin
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/conf
- $(INSTALL_DATA) $(CONF_FILES) $(RELSYSDIR)/examples/server_root/conf
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/htdocs/open
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/auth"
+ $(INSTALL_DATA) $(AUTH_FILES) "$(RELSYSDIR)/examples/server_root/auth"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/cgi-bin"
+ $(INSTALL_SCRIPT) $(CGI_FILES) "$(RELSYSDIR)/examples/server_root/cgi-bin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/conf"
+ $(INSTALL_DATA) $(CONF_FILES) "$(RELSYSDIR)/examples/server_root/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/htdocs/open"
$(INSTALL_DATA) $(OPEN_FILES) \
- $(RELSYSDIR)/examples/server_root/htdocs/open
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/htdocs/mnesia_open
+ "$(RELSYSDIR)/examples/server_root/htdocs/open"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/htdocs/mnesia_open"
$(INSTALL_DATA) $(MNESIA_OPEN_FILES) \
- $(RELSYSDIR)/examples/server_root/htdocs/mnesia_open
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/htdocs/misc
+ "$(RELSYSDIR)/examples/server_root/htdocs/mnesia_open"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/htdocs/misc"
$(INSTALL_DATA) $(MISC_FILES) \
- $(RELSYSDIR)/examples/server_root/htdocs/misc
+ "$(RELSYSDIR)/examples/server_root/htdocs/misc"
$(INSTALL_DIR) \
- $(RELSYSDIR)/examples/server_root/htdocs/secret/top_secret
+ "$(RELSYSDIR)/examples/server_root/htdocs/secret/top_secret"
$(INSTALL_DIR) \
- $(RELSYSDIR)/examples/server_root/htdocs/mnesia_secret/top_secret
+ "$(RELSYSDIR)/examples/server_root/htdocs/mnesia_secret/top_secret"
$(INSTALL_DATA) $(SECRET_FILES) \
- $(RELSYSDIR)/examples/server_root/htdocs/secret
+ "$(RELSYSDIR)/examples/server_root/htdocs/secret"
$(INSTALL_DATA) $(MNESIA_SECRET_FILES) \
- $(RELSYSDIR)/examples/server_root/htdocs/mnesia_secret
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/htdocs
- $(INSTALL_DATA) $(HTDOCS_FILES) $(RELSYSDIR)/examples/server_root/htdocs
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/icons
- $(INSTALL_DATA) $(ICON_FILES) $(RELSYSDIR)/examples/server_root/icons
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/ssl
- $(INSTALL_DATA) $(SSL_FILES) $(RELSYSDIR)/examples/server_root/ssl
- $(INSTALL_DIR) $(RELSYSDIR)/examples/server_root/logs
+ "$(RELSYSDIR)/examples/server_root/htdocs/mnesia_secret"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/htdocs"
+ $(INSTALL_DATA) $(HTDOCS_FILES) "$(RELSYSDIR)/examples/server_root/htdocs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/icons"
+ $(INSTALL_DATA) $(ICON_FILES) "$(RELSYSDIR)/examples/server_root/icons"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/ssl"
+ $(INSTALL_DATA) $(SSL_FILES) "$(RELSYSDIR)/examples/server_root/ssl"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/server_root/logs"
release_docs_spec:
diff --git a/lib/inets/priv/Makefile b/lib/inets/priv/Makefile
index 85da409e55..4dc521f618 100644
--- a/lib/inets/priv/Makefile
+++ b/lib/inets/priv/Makefile
@@ -57,8 +57,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_SCRIPT) $(EXECUTABLES) $(RELSYSDIR)/priv/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_SCRIPT) $(EXECUTABLES) "$(RELSYSDIR)/priv/bin"
release_docs_spec:
diff --git a/lib/inets/src/ftp/Makefile b/lib/inets/src/ftp/Makefile
index 19b93870df..426286f254 100644
--- a/lib/inets/src/ftp/Makefile
+++ b/lib/inets/src/ftp/Makefile
@@ -88,11 +88,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/ftp
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/ftp
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/ftp"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/ftp"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/src/http_client/Makefile b/lib/inets/src/http_client/Makefile
index d490e59929..850c790bd1 100644
--- a/lib/inets/src/http_client/Makefile
+++ b/lib/inets/src/http_client/Makefile
@@ -89,11 +89,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/http_client
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/http_client
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/http_client"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/http_client"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/src/http_lib/Makefile b/lib/inets/src/http_lib/Makefile
index aaf3cfb995..3ec6ce7436 100644
--- a/lib/inets/src/http_lib/Makefile
+++ b/lib/inets/src/http_lib/Makefile
@@ -87,11 +87,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/http_lib
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/http_lib
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/http_lib"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/http_lib"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/src/http_server/Makefile b/lib/inets/src/http_server/Makefile
index 60bb0d2527..67555d5f1c 100644
--- a/lib/inets/src/http_server/Makefile
+++ b/lib/inets/src/http_server/Makefile
@@ -123,11 +123,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/http_server
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/http_server
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/http_server"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/http_server"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/src/inets_app/Makefile b/lib/inets/src/inets_app/Makefile
index 6da6a1d79f..b8d923edd8 100644
--- a/lib/inets/src/inets_app/Makefile
+++ b/lib/inets/src/inets_app/Makefile
@@ -111,13 +111,13 @@ $(APPUP_TARGET): $(APPUP_SRC) ../../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/inets_app
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/inets_app
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/inets_app"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/inets_app"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/src/tftp/Makefile b/lib/inets/src/tftp/Makefile
index 759b70c8e4..a9df8d0319 100644
--- a/lib/inets/src/tftp/Makefile
+++ b/lib/inets/src/tftp/Makefile
@@ -39,8 +39,10 @@ RELSYSDIR = $(RELEASE_PATH)/lib/$(APPLICATION)-$(VSN)
# ----------------------------------------------------
# Target Specs
# ----------------------------------------------------
+BEHAVIOUR_MODULES= \
+ tftp
+
MODULES = \
- tftp \
tftp_binary \
tftp_engine \
tftp_file \
@@ -50,10 +52,13 @@ MODULES = \
HRL_FILES = tftp.hrl
-ERL_FILES = $(MODULES:%=%.erl)
+ERL_FILES= \
+ $(MODULES:%=%.erl) \
+ $(BEHAVIOUR_MODULES:%=%.erl)
TARGET_FILES= $(MODULES:%=$(EBIN)/%.$(EMULATOR))
+BEHAVIOUR_TARGET_FILES= $(BEHAVIOUR_MODULES:%=$(EBIN)/%.$(EMULATOR))
# ----------------------------------------------------
# FLAGS
@@ -72,10 +77,12 @@ ERL_COMPILE_FLAGS += \
# Targets
# ----------------------------------------------------
+$(TARGET_FILES): $(BEHAVIOUR_TARGET_FILES)
+
debug opt: $(TARGET_FILES)
clean:
- rm -f $(TARGET_FILES)
+ rm -f $(TARGET_FILES) $(BEHAVIOUR_TARGET_FILES)
rm -f core
docs:
@@ -86,11 +93,11 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/tftp
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src/tftp
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/tftp"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src/tftp"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(BEHAVIOUR_TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inets/test/Makefile b/lib/inets/test/Makefile
index 87ca60e4b3..7befa82272 100644
--- a/lib/inets/test/Makefile
+++ b/lib/inets/test/Makefile
@@ -234,7 +234,7 @@ endif
# Release directory specification
# ----------------------------------------------------
-RELTESTSYSDIR = $(RELEASE_PATH)/inets_test
+RELTESTSYSDIR = "$(RELEASE_PATH)/inets_test"
RELTESTSYSALLDATADIR = $(RELTESTSYSDIR)/all_SUITE_data
RELTESTSYSBINDIR = $(RELTESTSYSALLDATADIR)/bin
@@ -284,9 +284,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/test
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/test
- $(INSTALL_DATA) $(INETS_FILES) $(RELSYSDIR)/test
+ $(INSTALL_DIR) "$(RELSYSDIR)/test"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/test"
+ $(INSTALL_DATA) $(INETS_FILES) "$(RELSYSDIR)/test"
@for d in $(DATADIRS); do \
echo "installing data dir $$d"; \
if test -f $$d/TAR.exclude; then \
@@ -299,9 +299,9 @@ release_spec: opt
find $$d -name 'erl_crash.dump' >> $$d/TAR.exclude2; \
find $$d -name 'core' >> $$d/TAR.exclude2; \
find $$d -name '.cmake.state' >> $$d/TAR.exclude2; \
- tar cfX - $$d/TAR.exclude2 $$d | (cd $(RELSYSDIR)/test; tar xf -); \
+ tar cfX - $$d/TAR.exclude2 $$d | (cd "$(RELSYSDIR)/test"; tar xf -); \
else \
- tar cf - $$d | (cd $(RELSYSDIR)/test; tar xf -); \
+ tar cf - $$d | (cd "$(RELSYSDIR)/test"; tar xf -); \
fi; \
done
@@ -330,8 +330,8 @@ info:
@echo "INETS_SPECS = $(INETS_SPECS)"
@echo "INETS_FILES = $(INETS_FILES)"
@echo ""
- @echo "RELEASE_PATH = $(RELEASE_PATH)"
- @echo "RELSYSDIR = $(RELSYSDIR)"
+ @echo "RELEASE_PATH = "$(RELEASE_PATH)""
+ @echo "RELSYSDIR = "$(RELSYSDIR)""
@echo "RELTESTSYSDIR = $(RELTESTSYSDIR)"
@echo "RELTESTSYSALLDATADIR = $(RELTESTSYSALLDATADIR)"
@echo "RELTESTSYSBINDIR = $(RELTESTSYSBINDIR)"
diff --git a/lib/inviso/doc/src/Makefile b/lib/inviso/doc/src/Makefile
index 1b184ed78b..f00b10f29c 100644
--- a/lib/inviso/doc/src/Makefile
+++ b/lib/inviso/doc/src/Makefile
@@ -106,14 +106,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/inviso/src/Makefile b/lib/inviso/src/Makefile
index 1f2f8b1aff..292a2bec99 100644
--- a/lib/inviso/src/Makefile
+++ b/lib/inviso/src/Makefile
@@ -87,12 +87,12 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
-# $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+# $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/inviso/test/Makefile b/lib/inviso/test/Makefile
index c1df29d631..2650faa392 100644
--- a/lib/inviso/test/Makefile
+++ b/lib/inviso/test/Makefile
@@ -51,10 +51,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) inviso.spec inviso.cover $(ERL_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) inviso.spec inviso.cover $(ERL_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/jinterface/doc/src/Makefile b/lib/jinterface/doc/src/Makefile
index acd5307dee..858c97f187 100644
--- a/lib/jinterface/doc/src/Makefile
+++ b/lib/jinterface/doc/src/Makefile
@@ -160,17 +160,17 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html/java/$(JAVA_PKG_PATH)
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- (/bin/cp -rf ../html $(RELSYSDIR)/doc)
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html/java/$(JAVA_PKG_PATH)"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ (/bin/cp -rf ../html "$(RELSYSDIR)/doc")
# $(INSTALL_DATA) $(GIF_FILES) $(EXTRA_FILES) $(HTML_FILES) \
-# $(RELSYSDIR)/doc/html
-# $(INSTALL_DATA) $(JAVA_EXTRA_FILES) $(RELSYSDIR)/doc/html/java
-# $(INSTALL_DATA) $(TOP_HTML_FILES) $(RELSYSDIR)/doc
+# "$(RELSYSDIR)/doc/html"
+# $(INSTALL_DATA) $(JAVA_EXTRA_FILES) "$(RELSYSDIR)/doc/html/java"
+# $(INSTALL_DATA) $(TOP_HTML_FILES) "$(RELSYSDIR)/doc"
release_spec:
diff --git a/lib/jinterface/doc/src/notes.xml b/lib/jinterface/doc/src/notes.xml
index bf94077114..420e121389 100644
--- a/lib/jinterface/doc/src/notes.xml
+++ b/lib/jinterface/doc/src/notes.xml
@@ -30,6 +30,39 @@
</header>
<p>This document describes the changes made to the Jinterface application.</p>
+<section><title>Jinterface 1.5.6</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Correct spelling of registered (Thanks to Richard
+ Carlsson)</p>
+ <p>
+ Own Id: OTP-9925</p>
+ </item>
+ <item>
+ <p>
+ Java 1.5 has a bug where detecting codepoint offsets in
+ strings that are created by String.substring() gives
+ wrong results. The new implementation uses a different
+ method, avoinding the issue. (Thanks to Vlad Dumitrescu)</p>
+ <p>
+ Own Id: OTP-9927</p>
+ </item>
+ <item>
+ <p>
+ Improve error message when creating a too long
+ OtpErlangAtom. Also print the value that we tried to use
+ for the atom. (Thanks to Vlad Dumitrescu)</p>
+ <p>
+ Own Id: OTP-9928</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Jinterface 1.5.5</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/jinterface/java_src/com/ericsson/otp/erlang/Makefile b/lib/jinterface/java_src/com/ericsson/otp/erlang/Makefile
index 365798e68a..ec817aa39b 100644
--- a/lib/jinterface/java_src/com/ericsson/otp/erlang/Makefile
+++ b/lib/jinterface/java_src/com/ericsson/otp/erlang/Makefile
@@ -66,7 +66,7 @@ JARFLAGS=-cvf
JAVA_OPTIONS =
ifeq ($(TESTROOT),)
-RELEASE_PATH=$(ERL_TOP)/release/$(TARGET)
+RELEASE_PATH="$(ERL_TOP)/release/$(TARGET)"
else
RELEASE_PATH=$(TESTROOT)
endif
@@ -96,13 +96,13 @@ docs:
# include $(ERL_TOP)/make/otp_release_targets.mk
release release_docs release_tests release_html:
- $(MAKE) $(MFLAGS) RELEASE_PATH=$(RELEASE_PATH) $(TARGET_MAKEFILE) $@_spec
+ $(MAKE) $(MFLAGS) RELEASE_PATH="$(RELEASE_PATH)" $(TARGET_MAKEFILE) $@_spec
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/java_src/com/ericsson/otp/erlang
- $(INSTALL_DATA) $(JAVA_SRC) $(RELSYSDIR)/java_src/com/ericsson/otp/erlang
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(JAVA_DEST_ROOT)$(JARFILE) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/java_src/com/ericsson/otp/erlang"
+ $(INSTALL_DATA) $(JAVA_SRC) "$(RELSYSDIR)/java_src/com/ericsson/otp/erlang"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(JAVA_DEST_ROOT)$(JARFILE) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/jinterface/test/Makefile b/lib/jinterface/test/Makefile
index a85d0e7411..b70521c08d 100644
--- a/lib/jinterface/test/Makefile
+++ b/lib/jinterface/test/Makefile
@@ -80,6 +80,6 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(TEST_SPEC_FILE) $(COVER_FILE) $(ERL_FILES) $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(TEST_SPEC_FILE) $(COVER_FILE) $(ERL_FILES) "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
diff --git a/lib/jinterface/vsn.mk b/lib/jinterface/vsn.mk
index 9d8229e9fa..15423e5658 100644
--- a/lib/jinterface/vsn.mk
+++ b/lib/jinterface/vsn.mk
@@ -1 +1 @@
-JINTERFACE_VSN = 1.5.5
+JINTERFACE_VSN = 1.5.6
diff --git a/lib/kernel/doc/src/Makefile b/lib/kernel/doc/src/Makefile
index 214e994889..78e5f7bc26 100644
--- a/lib/kernel/doc/src/Makefile
+++ b/lib/kernel/doc/src/Makefile
@@ -155,18 +155,18 @@ $(SPECDIR)/specs_zlib_stub.xml:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man4
- $(INSTALL_DATA) $(MAN4_FILES) $(RELEASE_PATH)/man/man4
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man4"
+ $(INSTALL_DATA) $(MAN4_FILES) "$(RELEASE_PATH)/man/man4"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/kernel/doc/src/gen_sctp.xml b/lib/kernel/doc/src/gen_sctp.xml
index 579b7f1f74..e327a4f907 100644
--- a/lib/kernel/doc/src/gen_sctp.xml
+++ b/lib/kernel/doc/src/gen_sctp.xml
@@ -123,7 +123,7 @@
<p>Completely closes the socket and all associations on it. The unsent
data is flushed as in <c>eof/2</c>. The <c>close/1</c> call
is blocking or otherwise depending of the value of
- the <seealso marker="#option-linger">linger</seealso> socket
+ the <seealso marker="inet#option-linger">linger</seealso> socket
<seealso marker="#options">option</seealso>.
If <c>close</c> does not linger or linger timeout expires,
the call returns and the data is flushed in the background.</p>
@@ -309,8 +309,8 @@
<seealso marker="#option-active">passive</seealso> mode,
with <anno>SockType</anno> <c>seqpacket</c>,
and with reasonably large
- <seealso marker="#option-sndbuf">kernel</seealso> and driver
- <seealso marker="#option-buffer">buffers.</seealso></p>
+ <seealso marker="inet#option-sndbuf">kernel</seealso> and driver
+ <seealso marker="inet#option-buffer">buffers.</seealso></p>
</desc>
</func>
<func>
@@ -530,19 +530,8 @@
SCTP data interleaved with other inter-process messages.</p>
</item>
</list>
- <marker id="option-buffer"></marker>
</item>
- <tag><c>{buffer, integer()}</c></tag>
- <item>
- <p>Determines the size of the user-level software buffer used by
- the SCTP driver. Not to be confused with <c>sndbuf</c>
- and <c>recbuf</c> options which correspond to
- the kernel socket buffers. It is recommended
- to have <c>val(buffer) &gt;= max(val(sndbuf),val(recbuf))</c>.
- In fact, the <c>val(buffer)</c> is automatically set to
- the above maximum when <c>sndbuf</c> or <c>recbuf</c> values are set.</p>
- </item>
- <tag><c>{tos, integer()}</c></tag>
+ <tag><c>{tos, integer()}</c></tag>
<item>
<p>Sets the Type-Of-Service field on the IP datagrams being sent,
to the given value, which effectively determines a prioritization
@@ -567,19 +556,8 @@
<c>{IP,Port}</c> of the socket can be re-used immediately:
no waiting in the CLOSE_WAIT state is performed (may be
required for high-throughput servers).</p>
- <marker id="option-linger"></marker>
- </item>
- <tag><c>{linger, {true|false, integer()}</c></tag>
- <item>
- <p>Determines the timeout in seconds for flushing unsent data in the
- <c>gen_sctp:close/1</c> socket call. If the 1st component of the value
- tuple is <c>false</c>, the 2nd one is ignored, which means that
- <c>gen_sctp:close/1</c> returns immediately not waiting
- for data to be flushed. Otherwise, the 2nd component is
- the flushing time-out in seconds.</p>
- <marker id="option-sndbuf"></marker>
</item>
- <tag><c>{sndbuf, integer()}</c></tag>
+ <tag><c>{sndbuf, integer()}</c></tag>
<item>
<p>The size, in bytes, of the *kernel* send buffer for this socket.
Sending errors would occur for datagrams larger than
@@ -593,6 +571,15 @@
<c>val(sndbuf)</c>. Setting this option also adjusts
the size of the driver buffer (see <c>buffer</c> above).</p>
</item>
+
+ <tag><c>{sctp_module, module()}</c></tag>
+ <item> <p>
+ Override which callback module is used. Defaults to
+ <c>inet_sctp</c> for IPv4 and <c>inet6_sctp</c> for IPv6.
+ </p>
+ </item>
+
+
<tag><c>{sctp_rtoinfo, #sctp_rtoinfo{}}</c></tag>
<item>
<pre> #sctp_rtoinfo{
diff --git a/lib/kernel/doc/src/gen_tcp.xml b/lib/kernel/doc/src/gen_tcp.xml
index cf97607af1..11a0843c10 100644
--- a/lib/kernel/doc/src/gen_tcp.xml
+++ b/lib/kernel/doc/src/gen_tcp.xml
@@ -96,37 +96,47 @@ do_recv(Sock, Bs) ->
can be either a hostname, or an IP address.</p>
<p>The available options are:</p>
<taglist>
- <tag><c>list</c></tag>
- <item>
- <p>Received <c>Packet</c> is delivered as a list.</p>
- </item>
- <tag><c>binary</c></tag>
- <item>
- <p>Received <c>Packet</c> is delivered as a binary.</p>
- </item>
- <tag><c>{ip, ip_address()}</c></tag>
+ <tag><c>{ip, ip_address()}</c></tag>
<item>
<p>If the host has several network interfaces, this option
specifies which one to use.</p>
</item>
- <tag><c>{port, Port}</c></tag>
+
+ <tag><c>{ifaddr, ip_address()}</c></tag>
<item>
- <p>Specify which local port number to use.</p>
- </item>
+ <p>Same as <c>{ip, ip_address()}</c>. If the host has several network interfaces, this option
+ specifies which one to use.</p>
+ </item>
+
<tag><c>{fd, integer() >= 0}</c></tag>
<item>
<p>If a socket has somehow been connected without using
<c>gen_tcp</c>, use this option to pass the file
descriptor for it.</p>
</item>
- <tag><c>inet6</c></tag>
+
+ <tag><c>inet</c></tag>
<item>
+ <p>Set up the socket for IPv4.</p>
+ </item>
+
+ <tag><c>inet6</c></tag>
+ <item>
<p>Set up the socket for IPv6.</p>
</item>
- <tag><c>inet</c></tag>
+
+ <tag><c>{port, Port}</c></tag>
<item>
- <p>Set up the socket for IPv4.</p>
+ <p>Specify which local port number to use.</p>
</item>
+
+ <tag><c>{tcp_module, module()}</c></tag>
+ <item> <p>
+ Override which callback module is used. Defaults to
+ <c>inet_tcp</c> for IPv4 and <c>inet6_tcp</c> for IPv6.
+ </p>
+ </item>
+
<tag><c>Opt</c></tag>
<item>
<p>See
@@ -197,6 +207,13 @@ do_recv(Sock, Bs) ->
<c>gen_tcp</c>, use this option to pass the file
descriptor for it.</p>
</item>
+
+ <tag><c>{ifaddr, ip_address()}</c></tag>
+ <item>
+ <p>Same as <c>{ip, ip_address()}</c>. If the host has several network interfaces, this option
+ specifies which one to use.</p>
+ </item>
+
<tag><c>inet6</c></tag>
<item>
<p>Set up the socket for IPv6.</p>
@@ -205,6 +222,14 @@ do_recv(Sock, Bs) ->
<item>
<p>Set up the socket for IPv4.</p>
</item>
+
+ <tag><c>{tcp_module, module()}</c></tag>
+ <item> <p>
+ Override which callback module is used. Defaults to
+ <c>inet_tcp</c> for IPv4 and <c>inet6_tcp</c> for IPv6.
+ </p>
+ </item>
+
<tag><c>Opt</c></tag>
<item>
<p>See
@@ -299,7 +324,7 @@ do_recv(Sock, Bs) ->
<c><anno>Socket</anno></c>. The controlling process is the process which
receives messages from the socket. If called by any other
process than the current controlling process,
- <c>{error, eperm}</c> is returned.</p>
+ <c>{error, not_owner}</c> is returned.</p>
</desc>
</func>
<func>
diff --git a/lib/kernel/doc/src/gen_udp.xml b/lib/kernel/doc/src/gen_udp.xml
index daa9b7d887..726dc30546 100644
--- a/lib/kernel/doc/src/gen_udp.xml
+++ b/lib/kernel/doc/src/gen_udp.xml
@@ -72,6 +72,14 @@
<p>If the host has several network interfaces, this option
specifies which one to use.</p>
</item>
+
+ <tag><c>{ifaddr, ip_address()}</c></tag>
+ <item>
+ <p>Same as <c>{ip, ip_address()}</c>. If the host has several network interfaces, this option
+ specifies which one to use.</p>
+ </item>
+
+
<tag><c>{fd, integer() >= 0}</c></tag>
<item>
<p>If a socket has somehow been opened without using
@@ -86,6 +94,51 @@
<item>
<p>Set up the socket for IPv4.</p>
</item>
+
+ <tag><c>{udp_module, module()}</c></tag>
+ <item> <p>
+ Override which callback module is used. Defaults to
+ <c>inet_udp</c> for IPv4 and <c>inet6_udp</c> for IPv6.
+ </p>
+ </item>
+
+ <tag><c>{multicast_if, Address}</c></tag>
+ <item>
+ <p>Set the local device for a multicast socket.</p>
+ </item>
+
+ <tag><c>{multicast_loop, true | false}</c></tag>
+ <item>
+ <p>
+ When <c>true</c> sent multicast packets will be looped back to the local
+ sockets.
+ </p>
+ </item>
+
+ <tag><c>{multicast_ttl, Integer}</c></tag>
+ <item>
+ <p>
+ The <c>multicast_ttl</c> option changes the time-to-live (TTL) for
+ outgoing multicast datagrams in order to control the scope of the
+ multicasts.
+ </p>
+ <p>
+ Datagrams with a TTL of 1 are not forwarded beyond the local
+ network.
+ <br />Default: 1
+ </p>
+ </item>
+
+ <tag><c>{add_membership, {MultiAddress, InterfaceAddress}}</c></tag>
+ <item>
+ <p>Join a multicast group. </p>
+ </item>
+
+ <tag><c>{drop_membership, {MultiAddress, InterfaceAddress}}</c></tag>
+ <item>
+ <p>Leave multicast group.</p>
+ </item>
+
<tag><c>Opt</c></tag>
<item>
<p>See
@@ -136,7 +189,9 @@
<desc>
<p>Assigns a new controlling process <c><anno>Pid</anno></c> to
<c><anno>Socket</anno></c>. The controlling process is the process which
- receives messages from the socket.</p>
+ receives messages from the socket. If called by any other
+ process than the current controlling process,
+ <c>{error, not_owner}</c> is returned.</p>
</desc>
</func>
<func>
diff --git a/lib/kernel/doc/src/inet.xml b/lib/kernel/doc/src/inet.xml
index bf6c4cfb1a..096ddfd847 100644
--- a/lib/kernel/doc/src/inet.xml
+++ b/lib/kernel/doc/src/inet.xml
@@ -445,10 +445,34 @@ fe80::204:acff:fe17:bf38
flow control; the other side will not be able send
faster than the receiver can read.</p>
</item>
+
+ <tag><c>{bit8, clear | set | on | off}</c></tag>
+ <item>
+ <p>
+ Scans every byte in received data-packets and checks if the 8 bit
+ is set in any of them. Information is retrieved with
+ <c>inet:getopts/2</c>.
+ <note>Deprecated! Will be removed in Erlang/OTP R16.</note>
+ </p>
+ </item>
+
<tag><c>{broadcast, Boolean}</c>(UDP sockets)</tag>
<item>
<p>Enable/disable permission to send broadcasts.</p>
+ <marker id="option-buffer"></marker>
</item>
+
+ <tag><c>{buffer, Size}</c></tag>
+ <item>
+ <p>Determines the size of the user-level software buffer used by
+ the driver. Not to be confused with <c>sndbuf</c>
+ and <c>recbuf</c> options which correspond to
+ the kernel socket buffers. It is recommended
+ to have <c>val(buffer) &gt;= max(val(sndbuf),val(recbuf))</c>.
+ In fact, the <c>val(buffer)</c> is automatically set to
+ the above maximum when <c>sndbuf</c> or <c>recbuf</c> values are set.</p>
+ </item>
+
<tag><c>{delay_send, Boolean}</c></tag>
<item>
<p>Normally, when an Erlang process sends to a socket,
@@ -463,10 +487,19 @@ fe80::204:acff:fe17:bf38
real property of the socket. Needless to say it is an
implementation specific option. Default is <c>false</c>.</p>
</item>
+
+ <tag><c>{deliver, port | term}</c></tag>
+ <item> <p> When <c>{active, true}</c> delivers data on the forms
+ <c>port</c> : <c>{S, {data, [H1,..Hsz | Data]}}</c> or
+ <c>term</c> : <c>{tcp, S, [H1..Hsz | Data]}</c>.
+ </p>
+ </item>
+
<tag><c>{dontroute, Boolean}</c></tag>
<item>
<p>Enable/disable routing bypass for outgoing messages.</p>
</item>
+
<tag><c>{exit_on_close, Boolean}</c></tag>
<item>
<p>By default this option is set to <c>true</c>.</p>
@@ -476,6 +509,7 @@ fe80::204:acff:fe17:bf38
<seealso marker="gen_tcp#shutdown/2">gen_tcp:shutdown/2</seealso>
to shutdown the write side.</p>
</item>
+
<tag><c>{header, Size}</c></tag>
<item>
<p>This option is only meaningful if the <c>binary</c>
@@ -487,6 +521,15 @@ fe80::204:acff:fe17:bf38
example <c>Size == 2</c>, the data received will match
<c>[Byte1,Byte2|Binary]</c>.</p>
</item>
+
+ <tag><c>{high_watermark, Size}</c></tag>
+ <item> <p>
+ Sender is forced busy if sent and enqueued data
+ reaches the highwater mark.
+ <br /> Default: 8192 kB.
+ </p>
+ </item>
+
<tag><c>{keepalive, Boolean}</c>(TCP/IP sockets)</tag>
<item>
<p>Enables/disables periodic transmission on a connected
@@ -494,7 +537,43 @@ fe80::204:acff:fe17:bf38
the other end does not respond, the connection is
considered broken and an error message will be sent to
the controlling process. Default disabled.</p>
+ <marker id="option-linger"></marker>
</item>
+
+ <tag><c>{linger, {true|false, Seconds}}</c></tag>
+ <item>
+ <p>Determines the timeout in seconds for flushing unsent data in the
+ <c>close/1</c> socket call. If the 1st component of the value
+ tuple is <c>false</c>, the 2nd one is ignored, which means that
+ <c>close/1</c> returns immediately not waiting
+ for data to be flushed. Otherwise, the 2nd component is
+ the flushing time-out in seconds.</p>
+ </item>
+
+ <tag><c>{low_watermark, Size}</c></tag>
+ <item> <p>
+ If the port has reached its <c>high_watermark</c> it will
+ force busy onto senders. When the port data queue reaches the
+ <c>low_watermark</c> callers are no longer forced busy.
+ <br /> Default: 4096 kB.
+ </p>
+ </item>
+
+ <tag><c>{mode, Mode :: binary | list}</c></tag>
+ <item>
+ <p>Received <c>Packet</c> is delivered as defined by Mode.</p>
+ </item>
+
+ <tag><c>list</c></tag>
+ <item>
+ <p>Received <c>Packet</c> is delivered as a list.</p>
+ </item>
+
+ <tag><c>binary</c></tag>
+ <item>
+ <p>Received <c>Packet</c> is delivered as a binary.</p>
+ </item>
+
<tag><c>{nodelay, Boolean}</c>(TCP/IP sockets)</tag>
<item>
<p>If <c>Boolean == true</c>, the <c>TCP_NODELAY</c> option
@@ -578,6 +657,16 @@ fe80::204:acff:fe17:bf38
indicated length are accepted and not considered invalid due
to internal buffer limitations.</p>
</item>
+
+ <tag><c>{priority, Priority}</c></tag>
+ <item> <p>Set the protocol-defined priority for all packets to be sent
+ on this socket.</p>
+ </item>
+
+ <tag><c>{raw, Protocol, OptionNum, ValueBin}</c></tag>
+ <item> <p>See below.</p>
+ </item>
+
<tag><c>{read_packets, Integer}</c>(UDP sockets)</tag>
<item>
<p>Sets the max number of UDP packets to read without
@@ -589,7 +678,7 @@ fe80::204:acff:fe17:bf38
high the system can become unresponsive due to
UDP packet flooding.</p>
</item>
- <tag><c>{recbuf, Integer}</c></tag>
+ <tag><c>{recbuf, Size}</c></tag>
<item>
<p>Gives the size of the receive buffer to use for
the socket.</p>
@@ -618,9 +707,10 @@ fe80::204:acff:fe17:bf38
returns <c>{error,timeout}</c>. The recommended setting is
<c>true</c> which will automatically close the socket.
Default is <c>false</c> due to backward compatibility.</p>
+ <marker id="option-sndbuf"></marker>
</item>
- <tag><c>{sndbuf, Integer}</c></tag>
+ <tag><c>{sndbuf, Size}</c></tag>
<item>
<p>Gives the size of the send buffer to use for the socket.</p>
</item>
@@ -639,6 +729,7 @@ fe80::204:acff:fe17:bf38
not implemented. Use with caution.</p>
</item>
</taglist>
+
<p>In addition to the options mentioned above, <em>raw</em>
option specifications can be used. The raw options are
specified as a tuple of arity four, beginning with the tag
diff --git a/lib/kernel/doc/src/notes.xml b/lib/kernel/doc/src/notes.xml
index 9121186631..94624bf512 100644
--- a/lib/kernel/doc/src/notes.xml
+++ b/lib/kernel/doc/src/notes.xml
@@ -30,6 +30,133 @@
</header>
<p>This document describes the changes made to the Kernel application.</p>
+<section><title>Kernel 2.15.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Driver output has been corrected so output of large
+ binaries (> 4 GiB) now does not silently fail or crash
+ the emulator, but either outputs the binary or fails the
+ call. This means that writing a binary > 4 Gib to file
+ now works but on e.g 64-bit Windows (that has
+ scatter/gather I/O buffer segment lengths of 32 bits)
+ fails. The behaviour may change in the future to always
+ write the binary, in parts if necessary.</p>
+ <p>
+ Own Id: OTP-9820 Aux Id: OTP-9795 </p>
+ </item>
+ <item>
+ <p>
+ erts: minor fix for unnecessary condition erts: change
+ SENDFILE_CHUNK_SIZE from signed to unsigned (Thanks to
+ jovi zhang)</p>
+ <p>
+ Own Id: OTP-9872</p>
+ </item>
+ <item>
+ <p> Two contracts in <c>gen_sctp</c> have been corrected.
+ </p>
+ <p>
+ Own Id: OTP-9874</p>
+ </item>
+ <item>
+ <p>If a process calls a module with an running on_load
+ handler, the process is supposed to be suspended. But if
+ the module with the on_load handler was loading used
+ <c>code:load_binary/3</c>, the call would instead fail
+ with an <c>undef</c> exception.</p>
+ <p>
+ Own Id: OTP-9875</p>
+ </item>
+ <item>
+ <p>
+ File name and error reason is now returned if creation of
+ a cookie fails. (Thanks to Magnus Henoch)</p>
+ <p>
+ Own Id: OTP-9954</p>
+ </item>
+ <item>
+ <p>
+ Fix port leak in <c>zlib</c> when passing invalid data to
+ <c>compress,uncompress,zip,unzip,gzip,gunzip</c>.</p>
+ <p>
+ Own Id: OTP-9981</p>
+ </item>
+ <item>
+ <p>
+ Various typographical errors corrected in documentation
+ for the global, error_logger, etop, lists, ets and
+ supervisor modules and in the c_portdriver and kernel_app
+ documentation. (Thanks to Ricardo Catalinas Jim�nez)</p>
+ <p>
+ Own Id: OTP-9987</p>
+ </item>
+ <item>
+ <p> Fix returned error from gen_tcp:accept/1,2 when
+ running out of ports
+ <p>
+ The {error, enfile} return value is badly misleading and
+ confusing for this case, since the Posix ENFILE errno
+ value has a well-defined meaning that has nothing to do
+ with Erlang ports. The fix changes the return value to
+ {error, system_limit}, which is consistent with e.g.
+ various file(3) functions. inet:format_error/1 has also
+ been updated to support system_limit in the same manner
+ as file:format_error/1. (Thanks to Per Hedeland)</p></p>
+ <p>
+ Own Id: OTP-9990</p>
+ </item>
+ <item>
+ <p><c>erts_debug:size/1</c> has been corrected to take
+ sharing in the environment of funs into account. For funs
+ it used to always give the same result as
+ <c>erts_debug:flat_size/1</c>.</p>
+ <p>
+ Own Id: OTP-9991</p>
+ </item>
+ <item>
+ <p>
+ In some cases when the process doing file:sendfile
+ crashes while sending the file the efile_drv code would
+ not clean up after itself correctly. This has now been
+ fixed.</p>
+ <p>
+ Own Id: OTP-9993</p>
+ </item>
+ <item>
+ <p>
+ On BSD based platforms file:sendfile would sometime go
+ into an infinite loop when sending big files. This has
+ now been fixed.</p>
+ <p>
+ Own Id: OTP-9994</p>
+ </item>
+ <item>
+ <p>While <c>disk_log</c> eagerly collects logged terms
+ for better performance, collecting too much data may
+ choke the system and cause huge binaries to be
+ written.</p>
+ <p>The problem was addressed in OTP-9764, but the
+ situation was not improved in all cases.</p>
+ <p>(Thanks to Richard Carlsson.)</p>
+ <p>
+ Own Id: OTP-9999 Aux Id: OTP-9764 </p>
+ </item>
+ <item>
+ <p>
+ The documentation of .app files incorrectly said that the
+ default value for the <c>mod</c> parameter is
+ <c>undefined</c>. This is now corrected to <c>[]</c>.</p>
+ <p>
+ Own Id: OTP-10002</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Kernel 2.15</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/kernel/examples/Makefile b/lib/kernel/examples/Makefile
index fb27f8d438..21dfd0ec0e 100644
--- a/lib/kernel/examples/Makefile
+++ b/lib/kernel/examples/Makefile
@@ -47,8 +47,8 @@ RELSYSDIR = $(RELEASE_PATH)/lib/kernel-$(KERNEL_VSN)/examples
EXAMPLES = uds_dist
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
tar cf - $(EXAMPLES) | \
- (cd $(RELSYSDIR); tar xf - ; chmod -R ug+w $(EXAMPLES) )
+ (cd "$(RELSYSDIR)"; tar xf - ; chmod -R ug+w $(EXAMPLES) )
release_docs_spec:
diff --git a/lib/kernel/src/Makefile b/lib/kernel/src/Makefile
index 54f21eb2b8..a39864d6b7 100644
--- a/lib/kernel/src/Makefile
+++ b/lib/kernel/src/Makefile
@@ -198,13 +198,13 @@ $(EBIN)/erl_epmd.beam: $(ESRC)/erl_epmd.erl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/kernel/src/disk_log.erl b/lib/kernel/src/disk_log.erl
index f5f972c112..5b1efcd395 100644
--- a/lib/kernel/src/disk_log.erl
+++ b/lib/kernel/src/disk_log.erl
@@ -282,7 +282,8 @@ change_notify(Log, Pid, NewNotify) ->
-spec change_header(Log, Header) -> 'ok' | {'error', Reason} when
Log :: log(),
- Header :: {head, dlog_head_opt()} | {head_func, mfa()},
+ Header :: {head, dlog_head_opt()}
+ | {head_func, MFA :: {atom(), atom(), list()}},
Reason :: no_such_log | nonode | {read_only_mode, Log}
| {blocked_log, Log} | {badarg, head}.
change_header(Log, NewHead) ->
@@ -336,7 +337,9 @@ format_error(Error) ->
ok | {blocked, QueueLogRecords :: boolean()}}
| {node, Node :: node()}
| {distributed, Dist :: local | [node()]}
- | {head, Head :: none | {head, term()} | mfa()}
+ | {head, Head :: none
+ | {head, term()}
+ | (MFA :: {atom(), atom(), list()})}
| {no_written_items, NoWrittenItems ::non_neg_integer()}
| {full, Full :: boolean}
| {no_current_bytes, non_neg_integer()}
diff --git a/lib/kernel/src/disk_log.hrl b/lib/kernel/src/disk_log.hrl
index 259967650f..242a25a7a6 100644
--- a/lib/kernel/src/disk_log.hrl
+++ b/lib/kernel/src/disk_log.hrl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 1997-2011. All Rights Reserved.
+%% Copyright Ericsson AB 1997-2012. 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
@@ -74,7 +74,7 @@
| {distributed, Nodes :: [node()]}
| {notify, boolean()}
| {head, Head :: dlog_head_opt()}
- | {head_func, mfa()}
+ | {head_func, MFA :: {atom(), atom(), list()}}
| {mode, Mode :: dlog_mode()}.
-type dlog_options() :: [dlog_option()].
-type dlog_repair() :: 'truncate' | boolean().
diff --git a/lib/kernel/src/file.erl b/lib/kernel/src/file.erl
index d8033ee192..cdb984c333 100644
--- a/lib/kernel/src/file.erl
+++ b/lib/kernel/src/file.erl
@@ -1258,7 +1258,7 @@ sendfile_fallback_int(File, Sock, Bytes, ChunkSize, BytesSent)
when Bytes > BytesSent; Bytes == 0 ->
Size = if Bytes == 0 ->
ChunkSize;
- (Bytes - BytesSent + ChunkSize) > 0 ->
+ (Bytes - BytesSent) < ChunkSize ->
Bytes - BytesSent;
true ->
ChunkSize
diff --git a/lib/kernel/src/gen_sctp.erl b/lib/kernel/src/gen_sctp.erl
index d8954f0cf7..8fa963ec78 100644
--- a/lib/kernel/src/gen_sctp.erl
+++ b/lib/kernel/src/gen_sctp.erl
@@ -425,9 +425,10 @@ error_string(X) ->
erlang:error(badarg, [X]).
--spec controlling_process(Socket, Pid) -> ok when
+-spec controlling_process(Socket, Pid) -> ok | {error, Reason} when
Socket :: sctp_socket(),
- Pid :: pid().
+ Pid :: pid(),
+ Reason :: closed | not_owner | inet:posix().
controlling_process(S, Pid) when is_port(S), is_pid(Pid) ->
inet:udp_controlling_process(S, Pid);
diff --git a/lib/kernel/src/gen_tcp.erl b/lib/kernel/src/gen_tcp.erl
index ef6bfdf7f4..e6dfdadb03 100644
--- a/lib/kernel/src/gen_tcp.erl
+++ b/lib/kernel/src/gen_tcp.erl
@@ -31,7 +31,6 @@
-type option() ::
{active, true | false | once} |
- {bit8, clear | set | on | off} |
{buffer, non_neg_integer()} |
{delay_send, boolean()} |
{deliver, port | term} |
@@ -61,7 +60,6 @@
{tos, non_neg_integer()}.
-type option_name() ::
active |
- bit8 |
buffer |
delay_send |
deliver |
diff --git a/lib/kernel/src/gen_udp.erl b/lib/kernel/src/gen_udp.erl
index 8688799ae9..914854c65c 100644
--- a/lib/kernel/src/gen_udp.erl
+++ b/lib/kernel/src/gen_udp.erl
@@ -185,9 +185,10 @@ connect(S, Address, Port) when is_port(S) ->
Error
end.
--spec controlling_process(Socket, Pid) -> ok when
+-spec controlling_process(Socket, Pid) -> ok | {error, Reason} when
Socket :: socket(),
- Pid :: pid().
+ Pid :: pid(),
+ Reason :: closed | not_owner | inet:posix().
controlling_process(S, NewOwner) ->
inet:udp_controlling_process(S, NewOwner).
diff --git a/lib/kernel/src/inet.erl b/lib/kernel/src/inet.erl
index abaf4486dc..0bb5444dbb 100644
--- a/lib/kernel/src/inet.erl
+++ b/lib/kernel/src/inet.erl
@@ -1246,6 +1246,8 @@ udp_close(S) when is_port(S) ->
%% Set controlling process for TCP socket.
tcp_controlling_process(S, NewOwner) when is_port(S), is_pid(NewOwner) ->
case erlang:port_info(S, connected) of
+ {connected, NewOwner} ->
+ ok;
{connected, Pid} when Pid =/= self() ->
{error, not_owner};
undefined ->
@@ -1297,6 +1299,8 @@ tcp_sync_input(S, Owner, Flag) ->
%% Set controlling process for UDP or SCTP socket.
udp_controlling_process(S, NewOwner) when is_port(S), is_pid(NewOwner) ->
case erlang:port_info(S, connected) of
+ {connected, NewOwner} ->
+ ok;
{connected, Pid} when Pid =/= self() ->
{error, not_owner};
_ ->
diff --git a/lib/kernel/test/Makefile b/lib/kernel/test/Makefile
index 5dcaad3f5e..7bb3e3a365 100644
--- a/lib/kernel/test/Makefile
+++ b/lib/kernel/test/Makefile
@@ -140,12 +140,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(APP_FILES) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(APP_FILES) "$(RELSYSDIR)"
$(INSTALL_DATA) kernel.spec $(EMAKEFILE)\
- $(COVERFILE) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(COVERFILE) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/kernel/test/bif_SUITE.erl b/lib/kernel/test/bif_SUITE.erl
index 6276270d20..a2826f34df 100644
--- a/lib/kernel/test/bif_SUITE.erl
+++ b/lib/kernel/test/bif_SUITE.erl
@@ -260,23 +260,15 @@ spawn_opt2(Config) when is_list(Config) ->
?line P1 = spawn_opt(fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end,
- case heap_type() of
- separate ->
- [{fullsweep_after, 0},{min_heap_size, 1000}];
- shared ->
- []
- end
- ++ [link, {priority, max}]),
+ [{fullsweep_after, 0},{min_heap_size, 1000},
+ link, {priority, max}]),
?line receive
{P1, PV1} ->
?line Node = node(P1),
?line check_proc_vals(true, max, 0, 1000, PV1)
end,
?line P2 = spawn_opt(fun() -> Parent ! {self(), fetch_proc_vals(self())} end,
- case heap_type() of
- separate -> [{min_heap_size, 10}];
- shared -> []
- end),
+ [{min_heap_size, 10}]),
?line receive
{P2, PV2} ->
?line Node = node(P2),
@@ -295,13 +287,8 @@ spawn_opt3(Config) when is_list(Config) ->
fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end,
- case heap_type() of
- separate ->
- [{fullsweep_after,0}, {min_heap_size,1000}];
- shared ->
- []
- end
- ++ [link, {priority, max}]),
+ [{fullsweep_after,0}, {min_heap_size,1000},
+ link, {priority, max}]),
?line receive
{P1, PV1} ->
?line Node = node(P1),
@@ -309,10 +296,7 @@ spawn_opt3(Config) when is_list(Config) ->
end,
?line P2 = spawn_opt(Node,
fun() -> Parent ! {self(), fetch_proc_vals(self())} end,
- case heap_type() of
- separate -> [{min_heap_size, 10}];
- shared -> []
- end),
+ [{min_heap_size, 10}]),
?line receive
{P2, PV2} ->
?line Node = node(P2),
@@ -333,13 +317,8 @@ spawn_opt4(Config) when is_list(Config) ->
[fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end],
- case heap_type() of
- separate ->
- [{fullsweep_after,0}, {min_heap_size,1000}];
- shared ->
- []
- end
- ++ [link, {priority, max}]),
+ [{fullsweep_after,0}, {min_heap_size,1000},
+ link, {priority, max}]),
?line receive
{P1, PV1} ->
?line Node = node(P1),
@@ -350,10 +329,7 @@ spawn_opt4(Config) when is_list(Config) ->
[fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end],
- case heap_type() of
- separate -> [{min_heap_size, 10}];
- shared -> []
- end),
+ [{min_heap_size, 10}]),
?line receive
{P2, PV2} ->
?line Node = node(P2),
@@ -374,13 +350,8 @@ spawn_opt5(Config) when is_list(Config) ->
[fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end],
- case heap_type() of
- separate ->
- [{fullsweep_after,0}, {min_heap_size,1000}];
- shared ->
- []
- end
- ++ [link, {priority, max}]),
+ [{fullsweep_after,0}, {min_heap_size,1000},
+ link, {priority, max}]),
?line receive
{P1, PV1} ->
?line Node = node(P1),
@@ -392,10 +363,7 @@ spawn_opt5(Config) when is_list(Config) ->
[fun() ->
Parent ! {self(), fetch_proc_vals(self())}
end],
- case heap_type() of
- separate -> [{min_heap_size, 10}];
- shared -> []
- end),
+ [{min_heap_size, 10}]),
?line receive
{P2, PV2} ->
?line Node = node(P2),
@@ -532,34 +500,19 @@ spawn_failures(Config) when is_list(Config) ->
check_proc_vals(Link, Priority, FullsweepAfter, MinHeapSize, {Ls, P, FA, HS}) ->
?line Link = lists:member(self(), Ls),
?line Priority = P,
- ?line case heap_type() of
- separate ->
- ?line FullsweepAfter = FA,
- ?line true = (HS >= MinHeapSize);
- shared ->
- ?line ok
- end,
+ FullsweepAfter = FA,
+ true = (HS >= MinHeapSize),
?line ok.
fetch_proc_vals(Pid) ->
?line PI = process_info(Pid),
?line {value,{links, Ls}} = lists:keysearch(links, 1, PI),
?line {value,{priority,P}} = lists:keysearch(priority, 1, PI),
- ?line {FA, HS}
- = case heap_type() of
- separate ->
- ?line {value,
- {garbage_collection,
- Gs}} = lists:keysearch(garbage_collection, 1, PI),
- ?line {value,
- {fullsweep_after,
- Fa}} = lists:keysearch(fullsweep_after, 1, Gs),
- ?line {value,
- {heap_size,Hs}} = lists:keysearch(heap_size, 1, PI),
- ?line {Fa, Hs};
- shared ->
- {undefined, undefined}
- end,
+ {value,{garbage_collection,Gs}} =
+ lists:keysearch(garbage_collection, 1, PI),
+ {value,{fullsweep_after,FA}} =
+ lists:keysearch(fullsweep_after, 1, Gs),
+ {value,{heap_size,HS}} = lists:keysearch(heap_size, 1, PI),
?line {Ls, P, FA, HS}.
% This testcase should probably be moved somewhere else
@@ -650,12 +603,3 @@ stop_node(Node) ->
run_fun(Fun) ->
Fun().
-
-heap_type() ->
- case catch erlang:system_info(heap_type) of
- shared -> shared;
- unified -> shared;
- _ -> separate
- end.
-
-
diff --git a/lib/kernel/test/code_SUITE.erl b/lib/kernel/test/code_SUITE.erl
index 2c59351600..3e8bdaf1ff 100644
--- a/lib/kernel/test/code_SUITE.erl
+++ b/lib/kernel/test/code_SUITE.erl
@@ -501,7 +501,7 @@ sticky_dir(doc) -> ["Test that a module with the same name as a module in ",
"a sticky directory cannot be loaded."];
sticky_dir(Config) when is_list(Config) ->
MyDir=filename:dirname(code:which(?MODULE)),
- ?line {ok, Node}=?t:start_node(sticky_dir, slave,[{args, "-pa "++MyDir}]),
+ ?line {ok, Node}=?t:start_node(sticky_dir, slave,[{args, "-pa \""++MyDir++"\""}]),
File=filename:join([?config(data_dir, Config), "calendar"]),
?line Ret=rpc:call(Node, ?MODULE, sticky_compiler, [File]),
case Ret of
@@ -822,7 +822,7 @@ load_cached(Config) when is_list(Config) ->
?line WD = filename:dirname(code:which(?MODULE)),
?line {ok,Node} =
?t:start_node(code_cache_node, peer, [{args,
- "-pa " ++ WD},
+ "-pa \"" ++ WD ++ "\""},
{erl, [this]}]),
CCTabCreated = fun(Tab) ->
case ets:info(Tab, name) of
@@ -907,7 +907,7 @@ add_and_rehash(Config) when is_list(Config) ->
?line WD = filename:dirname(code:which(?MODULE)),
?line {ok,Node} =
?t:start_node(code_cache_node, peer, [{args,
- "-pa " ++ WD},
+ "-pa \"" ++ WD ++ "\""},
{erl, [this]}]),
CCTabCreated = fun(Tab) ->
case ets:info(Tab, name) of
diff --git a/lib/kernel/test/disk_log_SUITE.erl b/lib/kernel/test/disk_log_SUITE.erl
index ad987fe7a7..0c3f5c3514 100644
--- a/lib/kernel/test/disk_log_SUITE.erl
+++ b/lib/kernel/test/disk_log_SUITE.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 1997-2011. All Rights Reserved.
+%% Copyright Ericsson AB 1997-2012. 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
@@ -90,7 +90,7 @@
evil/1,
- otp_6278/1]).
+ otp_6278/1, otp_10131/1]).
-export([head_fun/1, hf/0, lserv/1,
measure/0, init_m/1, xx/0, head_exit/0, slow_header/1]).
@@ -124,7 +124,7 @@
[halt_int, wrap_int, halt_ext, wrap_ext, read_mode, head,
notif, new_idx_vsn, reopen, block, unblock, open, close,
error, chunk, truncate, many_users, info, change_size,
- change_attribute, distribution, evil, otp_6278]).
+ change_attribute, distribution, evil, otp_6278, otp_10131]).
%% The following two lists should be mutually exclusive. To skip a case
%% on VxWorks altogether, use the kernel.spec.vxworks file instead.
@@ -153,7 +153,7 @@ all() ->
{group, open}, {group, close}, {group, error}, chunk,
truncate, many_users, {group, info},
{group, change_size}, change_attribute,
- {group, distribution}, evil, otp_6278].
+ {group, distribution}, evil, otp_6278, otp_10131].
groups() ->
[{halt_int, [], [halt_int_inf, {group, halt_int_sz}]},
@@ -4915,6 +4915,22 @@ otp_6278(Conf) when is_list(Conf) ->
end,
?line error_logger:delete_report_handler(?MODULE).
+otp_10131(suite) -> [];
+otp_10131(doc) -> ["OTP-10131. head_func type."];
+otp_10131(Conf) when is_list(Conf) ->
+ Dir = ?privdir(Conf),
+ Log = otp_10131,
+ File = filename:join(Dir, lists:concat([Log, ".LOG"])),
+ HeadFunc = {?MODULE, head_fun, [{ok,"head"}]},
+ {ok, Log} = disk_log:open([{name,Log},{file,File},
+ {head_func, HeadFunc}]),
+ HeadFunc = info(Log, head, undef),
+ HeadFunc2 = {?MODULE, head_fun, [{ok,"head2"}]},
+ ok = disk_log:change_header(Log, {head_func, HeadFunc2}),
+ HeadFunc2 = info(Log, head, undef),
+ ok = disk_log:close(Log),
+ ok.
+
mark(FileName, What) ->
{ok,Fd} = file:open(FileName, [raw, binary, read, write]),
{ok,_} = file:position(Fd, 4),
diff --git a/lib/kernel/test/gen_tcp_misc_SUITE.erl b/lib/kernel/test/gen_tcp_misc_SUITE.erl
index c74a258af9..1592399996 100644
--- a/lib/kernel/test/gen_tcp_misc_SUITE.erl
+++ b/lib/kernel/test/gen_tcp_misc_SUITE.erl
@@ -24,7 +24,8 @@
-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1,
init_per_group/2,end_per_group/2,
- controlling_process/1, no_accept/1, close_with_pending_output/1,
+ controlling_process/1, controlling_process_self/1,
+ no_accept/1, close_with_pending_output/1,
data_before_close/1, iter_max_socks/1, get_status/1,
passive_sockets/1, accept_closed_by_other_process/1,
init_per_testcase/2, end_per_testcase/2,
@@ -58,7 +59,7 @@ end_per_testcase(_Func, Config) ->
suite() -> [{ct_hooks,[ts_install_cth]}].
all() ->
- [controlling_process, no_accept,
+ [controlling_process, controlling_process_self, no_accept,
close_with_pending_output, data_before_close,
iter_max_socks, passive_sockets,
accept_closed_by_other_process, otp_3924, closed_socket,
@@ -307,6 +308,32 @@ not_owner(S) ->
ok
end.
+controlling_process_self(doc) ->
+ ["Open a listen port and assign the controlling process to "
+ "it self, then exit and make sure the port is closed properly."];
+controlling_process_self(Config) when is_list(Config) ->
+ S = self(),
+ process_flag(trap_exit,true),
+ spawn_link(fun() ->
+ {ok,Sock} = gen_tcp:listen(0,[]),
+ S ! {socket, Sock},
+ ok = gen_tcp:controlling_process(Sock,self()),
+ S ! done
+ end),
+ receive
+ done ->
+ receive
+ {socket,Sock} ->
+ process_flag(trap_exit,false),
+ %% Make sure the port is invalid after process crash
+ {error,einval} = inet:port(Sock)
+ end;
+ Msg when element(1,Msg) /= socket ->
+ process_flag(trap_exit,false),
+ exit({unknown_msg,Msg})
+ end.
+
+
no_accept(doc) ->
["Open a listen port and connect to it, then close the listen port ",
"without doing any accept. The connected socket should receive ",
@@ -2044,7 +2071,7 @@ send_timeout_active(Config) when is_list(Config) ->
?line {error,timeout} =
Loop(fun() ->
receive
- {tcp, Sock, _Data} ->
+ {tcp, _Sock, _Data} ->
inet:setopts(A, [{active, once}]),
Res = gen_tcp:send(A,lists:duplicate(1000, $a)),
%erlang:display(Res),
@@ -2536,7 +2563,7 @@ otp_8102_do(LSocket, PortNum, {Bin,PType}) ->
otp_9389(doc) -> ["Verify packet_size handles long HTTP header lines"];
otp_9389(suite) -> [];
otp_9389(Config) when is_list(Config) ->
- ?line {ok, LS} = gen_tcp:listen(0, []),
+ ?line {ok, LS} = gen_tcp:listen(0, [{active,false}]),
?line {ok, {_, PortNum}} = inet:sockname(LS),
io:format("Listening on ~w with port number ~p\n", [LS, PortNum]),
OrigLinkHdr = "/" ++ string:chars($S, 8192),
diff --git a/lib/kernel/test/init_SUITE.erl b/lib/kernel/test/init_SUITE.erl
index b39fadd65f..e3fa4642b7 100644
--- a/lib/kernel/test/init_SUITE.erl
+++ b/lib/kernel/test/init_SUITE.erl
@@ -608,7 +608,7 @@ boot2(Config) when is_list(Config) ->
%% Absolute boot file name
Boot = filename:join([code:root_dir(), "bin", "start_sasl"]),
- Args = args() ++ " -boot " ++ Boot,
+ Args = args() ++ " -boot \"" ++ Boot++"\"",
?line {ok, Node} = start_node(init_test, Args),
?line stop_node(Node),
@@ -618,7 +618,7 @@ boot2(Config) when is_list(Config) ->
%% converted to backslashes.
Win_boot = lists:map(fun($/) -> $\\; (C) -> C end,
Boot),
- Args2 = args() ++ " -boot " ++ Win_boot,
+ Args2 = args() ++ " -boot \"" ++ Win_boot ++ "\"",
?line {ok, Node2} = start_node(init_test, Args2),
?line stop_node(Node2);
_ ->
diff --git a/lib/kernel/test/interactive_shell_SUITE.erl b/lib/kernel/test/interactive_shell_SUITE.erl
index b2308dd321..96e45cc23f 100644
--- a/lib/kernel/test/interactive_shell_SUITE.erl
+++ b/lib/kernel/test/interactive_shell_SUITE.erl
@@ -251,7 +251,7 @@ rtnode(Commands,Nodename,ErlPrefix) ->
?line {skip, Reason2};
Tempdir ->
?line SPid =
- start_runerl_node(RunErl,ErlPrefix++Erl,
+ start_runerl_node(RunErl,ErlPrefix++"\\\""++Erl++"\\\"",
Tempdir,Nodename),
?line CPid = start_toerl_server(ToErl,Tempdir),
?line erase(getline_skipped),
@@ -487,7 +487,7 @@ start_runerl_node(RunErl,Erl,Tempdir,Nodename) ->
" -setcookie "++atom_to_list(erlang:get_cookie())
end,
spawn(fun() ->
- os:cmd(RunErl++" "++Tempdir++"/ "++Tempdir++" \""++
+ os:cmd("\""++RunErl++"\" "++Tempdir++"/ "++Tempdir++" \""++
Erl++XArg++"\"")
end).
@@ -518,7 +518,7 @@ try_to_erl(Command, N) ->
end.
toerl_server(Parent,ToErl,Tempdir) ->
- Port = try_to_erl(ToErl++" "++Tempdir++"/ 2>/dev/null",8),
+ Port = try_to_erl("\""++ToErl++"\" "++Tempdir++"/ 2>/dev/null",8),
case Port of
P when is_port(P) ->
Parent ! {self(),started};
diff --git a/lib/kernel/vsn.mk b/lib/kernel/vsn.mk
index 76d3003ff4..c494f8a864 100644
--- a/lib/kernel/vsn.mk
+++ b/lib/kernel/vsn.mk
@@ -1 +1 @@
-KERNEL_VSN = 2.15.1
+KERNEL_VSN = 2.15.2
diff --git a/lib/megaco/Makefile b/lib/megaco/Makefile
index 9dc84c122c..fc8f408b0a 100644
--- a/lib/megaco/Makefile
+++ b/lib/megaco/Makefile
@@ -49,11 +49,14 @@ VSN=$(MEGACO_VSN)
DIR_NAME = megaco_src-$(VSN)$(PRE_VSN)
+nullstring :=
+space := $(nullstring) # a space at the end
+
ifndef APP_RELEASE_DIR
ifndef TESTROOT
APP_RELEASE_DIR = /tmp
else
- APP_RELEASE_DIR = $(TESTROOT)
+ APP_RELEASE_DIR = $(subst $(space),\ ,$(TESTROOT))
endif
endif
@@ -151,7 +154,7 @@ version:
# Application install (of a app built from source) targets
# ----------------------------------------------------
app_install:
- $(MAKE) TESTROOT=$(APP_INSTALL_DIR) release
+ $(MAKE) TESTROOT="$(APP_INSTALL_DIR)" release
# ----------------------------------------------------
@@ -185,20 +188,20 @@ TAR.exclude2: Makefile TAR.exclude
(cd ..; find megaco -name '.cmake.state' >> megaco/TAR.exclude2)
$(APP_DIR): tar_exclude
- mkdir -p $(APP_DIR); \
+ mkdir -p "$(subst $(space),\ ,$@)"; \
(cd ..; tar cfX - megaco/TAR.exclude2 megaco) | \
- (cd $(APP_DIR); tar xf -); \
- mv $(APP_DIR)/megaco/* $(APP_DIR)/; \
- mkdir $(APP_DIR)/autoconf; \
- cp autoconf/config.guess $(APP_DIR)/autoconf/; \
- cp autoconf/config.sub $(APP_DIR)/autoconf/; \
- cp autoconf/install-sh $(APP_DIR)/autoconf/; \
- rmdir $(APP_DIR)/megaco
+ (cd "$(subst $(space),\ ,$@)"; tar xf -); \
+ mv "$(subst $(space),\ ,$@)"/megaco/* "$(subst $(space),\ ,$@)"/; \
+ mkdir $(subst $(space),\ ,$@)/autoconf; \
+ cp autoconf/config.guess "$(subst $(space),\ ,$@)"/autoconf/; \
+ cp autoconf/config.sub "$(subst $(space),\ ,$@)"/autoconf/; \
+ cp autoconf/install-sh "$(subst $(space),\ ,$@)"/autoconf/; \
+ rmdir "$(subst $(space),\ ,$@)"/megaco
tar: $(APP_TAR_FILE)
$(APP_TAR_FILE): $(APP_DIR)
- (cd $(APP_RELEASE_DIR); gtar zcf $(APP_TAR_FILE) $(DIR_NAME))
+ (cd "$(APP_RELEASE_DIR)"; gtar zcf "$(subst $(space),\ ,$@)" $(DIR_NAME))
dialyzer_plt: $(DIA_PLT)
diff --git a/lib/megaco/doc/src/Makefile b/lib/megaco/doc/src/Makefile
index 137f0315d8..493304523e 100644
--- a/lib/megaco/doc/src/Makefile
+++ b/lib/megaco/doc/src/Makefile
@@ -164,16 +164,16 @@ info:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELSYSDIR)/doc/standard
- $(INSTALL_DATA) $(STANDARDS) $(RELSYSDIR)/doc/standard
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/standard"
+ $(INSTALL_DATA) $(STANDARDS) "$(RELSYSDIR)/doc/standard"
release_spec:
diff --git a/lib/megaco/examples/meas/Makefile.in b/lib/megaco/examples/meas/Makefile.in
index 6af7ef6c65..607d81d440 100644
--- a/lib/megaco/examples/meas/Makefile.in
+++ b/lib/megaco/examples/meas/Makefile.in
@@ -131,12 +131,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(EXAMPLE_RELSYSDIR)
- $(INSTALL_DIR) $(MEAS_RELSYSDIR)
- $(INSTALL_DATA) $(MESSAGE_PACKAGES) $(MEAS_RELSYSDIR)
- $(INSTALL_DATA) $(SCRIPT_SKELETONS) $(MEAS_RELSYSDIR)
- $(INSTALL_DATA) $(TARGET_FILES) $(MEAS_RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(MEAS_RELSYSDIR)
+ $(INSTALL_DIR) "$(EXAMPLE_RELSYSDIR)"
+ $(INSTALL_DIR) "$(MEAS_RELSYSDIR)"
+ $(INSTALL_DATA) $(MESSAGE_PACKAGES) "$(MEAS_RELSYSDIR)"
+ $(INSTALL_DATA) $(SCRIPT_SKELETONS) "$(MEAS_RELSYSDIR)"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(MEAS_RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) "$(MEAS_RELSYSDIR)"
release_docs_spec:
diff --git a/lib/megaco/examples/meas/megaco_codec_mstone_lib.erl b/lib/megaco/examples/meas/megaco_codec_mstone_lib.erl
index ca8016d65f..9af88d9f50 100644
--- a/lib/megaco/examples/meas/megaco_codec_mstone_lib.erl
+++ b/lib/megaco/examples/meas/megaco_codec_mstone_lib.erl
@@ -100,7 +100,6 @@ display_system_info() ->
OtpRel = otp_release(),
SysVer = system_version(),
SysHT = heap_type(),
- SysGHSz = global_heaps_size(),
SysSMP = smp_support(),
SysNumSched = schedulers(),
SysProcLimit = process_limit(),
@@ -113,7 +112,6 @@ display_system_info() ->
io:format("OTP release: ~s~n", [OtpRel]),
io:format("System version: ~s~n", [SysVer]),
io:format("Heap type: ~s~n", [SysHT]),
- io:format("Global heap size: ~s~n", [SysGHSz]),
io:format("Thread support: ~s~n", [SysThreads]),
io:format("Thread pool size: ~s~n", [SysTPSz]),
io:format("Process limit: ~s~n", [SysProcLimit]),
@@ -137,9 +135,6 @@ system_version() ->
heap_type() ->
system_info(heap_type, any).
-global_heaps_size() ->
- system_info(global_heaps_size, any).
-
smp_support() ->
system_info(smp_support, any).
diff --git a/lib/megaco/examples/simple/Makefile b/lib/megaco/examples/simple/Makefile
index f91d1d886f..261acbb479 100644
--- a/lib/megaco/examples/simple/Makefile
+++ b/lib/megaco/examples/simple/Makefile
@@ -139,9 +139,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DIR) $(RELSYSDIR)/examples/simple
- $(INSTALL_DATA) $(ERL_FILES) $(TARGET_FILES) $(RELSYSDIR)/examples/simple
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/simple"
+ $(INSTALL_DATA) $(ERL_FILES) $(TARGET_FILES) "$(RELSYSDIR)/examples/simple"
release_docs_spec:
diff --git a/lib/megaco/src/app/Makefile b/lib/megaco/src/app/Makefile
index 01dfb9b860..a7b458845d 100644
--- a/lib/megaco/src/app/Makefile
+++ b/lib/megaco/src/app/Makefile
@@ -108,14 +108,14 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/app
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/app
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/app"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/app"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/megaco/src/binary/Makefile b/lib/megaco/src/binary/Makefile
index d594f34f43..77b06c81d3 100644
--- a/lib/megaco/src/binary/Makefile
+++ b/lib/megaco/src/binary/Makefile
@@ -194,11 +194,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/binary
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(ASN1_FILES) $(RELSYSDIR)/src/binary
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/binary"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(ASN1_FILES) "$(RELSYSDIR)/src/binary"
release_docs_spec:
diff --git a/lib/megaco/src/engine/Makefile b/lib/megaco/src/engine/Makefile
index 3943f4b957..ae2fadb3fc 100644
--- a/lib/megaco/src/engine/Makefile
+++ b/lib/megaco/src/engine/Makefile
@@ -42,9 +42,14 @@ RELSYSDIR = $(RELEASE_PATH)/lib/megaco-$(VSN)
include modules.mk
-ERL_FILES = $(MODULES:%=%.erl)
+ERL_FILES = \
+ $(MODULES:%=%.erl) \
+ $(BEHAVIOUR_MODULES:%=%.erl)
-TARGET_FILES = \
+BEHAVIOUR_TARGET_FILES= \
+ $(BEHAVIOUR_MODULES:%=$(EBIN)/%.$(EMULATOR))
+
+TARGET_FILES = \
$(MODULES:%=$(EBIN)/%.$(EMULATOR))
@@ -65,19 +70,23 @@ ERL_COMPILE_FLAGS += \
# ----------------------------------------------------
# Targets
# ----------------------------------------------------
+
+$(TARGET_FILES): $(BEHAVIOUR_TARGET_FILES)
+
debug:
@${MAKE} TYPE=debug opt
opt: $(TARGET_FILES)
clean:
- rm -f $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
+ rm -f $(BEHAVIOUR_TARGET_FILES) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
rm -f errs core *~
docs:
info:
@echo "MODULES = $(MODULES)"
+ @echo "BEHAVIOUR_MODULES = $(BEHAVIOUR_MODULES)"
@echo ""
@@ -88,12 +97,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/engine
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/engine
- $(INSTALL_DIR) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(BEHAVIOUR_TARGET_FILES) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/engine"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/engine"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/megaco/src/engine/modules.mk b/lib/megaco/src/engine/modules.mk
index 4bc57cd63e..6e2f9246f0 100644
--- a/lib/megaco/src/engine/modules.mk
+++ b/lib/megaco/src/engine/modules.mk
@@ -23,7 +23,6 @@ BEHAVIOUR_MODULES = \
megaco_transport
MODULES = \
- $(BEHAVIOUR_MODULES) \
megaco_config_misc \
megaco_config \
megaco_digit_map \
diff --git a/lib/megaco/src/flex/Makefile.in b/lib/megaco/src/flex/Makefile.in
index 7d82644246..976ecaa4f7 100644
--- a/lib/megaco/src/flex/Makefile.in
+++ b/lib/megaco/src/flex/Makefile.in
@@ -271,16 +271,16 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/flex
- $(INSTALL_DIR) $(RELSYSDIR)/priv/lib
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/flex
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/flex"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/flex"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
ifeq ($(ENABLE_MEGACO_FLEX_SCANNER),true)
- $(INSTALL_DATA) $(FLEX_FILES) $(C_TARGETS) $(RELSYSDIR)/src/flex
- $(INSTALL_PROGRAM) $(SOLIBS) $(RELSYSDIR)/priv/lib
+ $(INSTALL_DATA) $(FLEX_FILES) $(C_TARGETS) "$(RELSYSDIR)/src/flex"
+ $(INSTALL_PROGRAM) $(SOLIBS) "$(RELSYSDIR)/priv/lib"
endif
diff --git a/lib/megaco/src/tcp/Makefile b/lib/megaco/src/tcp/Makefile
index 0bd4b7c4ee..efc76bb2c5 100644
--- a/lib/megaco/src/tcp/Makefile
+++ b/lib/megaco/src/tcp/Makefile
@@ -89,11 +89,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/tcp
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/tcp
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/tcp"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/tcp"
release_docs_spec:
diff --git a/lib/megaco/src/text/Makefile b/lib/megaco/src/text/Makefile
index b2e8e762dd..2c7703cd33 100644
--- a/lib/megaco/src/text/Makefile
+++ b/lib/megaco/src/text/Makefile
@@ -130,11 +130,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(BEAM_TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/text
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_YRL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/text
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(BEAM_TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/text"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_YRL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/text"
release_docs_spec:
diff --git a/lib/megaco/src/udp/Makefile b/lib/megaco/src/udp/Makefile
index 64b6478c2c..db9bb72d82 100644
--- a/lib/megaco/src/udp/Makefile
+++ b/lib/megaco/src/udp/Makefile
@@ -89,11 +89,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/udp
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/udp
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/udp"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/udp"
release_docs_spec:
diff --git a/lib/megaco/test/Makefile b/lib/megaco/test/Makefile
index 88f6f06e73..b1bca10ca8 100644
--- a/lib/megaco/test/Makefile
+++ b/lib/megaco/test/Makefile
@@ -748,11 +748,11 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(RELTEST_FILES) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(RELTEST_FILES) "$(RELSYSDIR)"
# $(INSTALL_DATA) $(TEST_SPEC_FILE) $(COVER_SPEC_FILE) \
# $(HRL_FILES) $(ERL_FILES) \
-# $(RELSYSDIR)
+# "$(RELSYSDIR)"
#
- chmod -R u+w $(RELSYSDIR)
+ chmod -R u+w "$(RELSYSDIR)"
diff --git a/lib/mnesia/doc/src/Makefile b/lib/mnesia/doc/src/Makefile
index 1ac5760510..173e43ac1f 100644
--- a/lib/mnesia/doc/src/Makefile
+++ b/lib/mnesia/doc/src/Makefile
@@ -142,13 +142,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/mnesia/doc/src/notes.xml b/lib/mnesia/doc/src/notes.xml
index a300fcc12d..612ccb5ee8 100644
--- a/lib/mnesia/doc/src/notes.xml
+++ b/lib/mnesia/doc/src/notes.xml
@@ -38,7 +38,37 @@
thus constitutes one section in this document. The title of each
section is the version number of Mnesia.</p>
- <section><title>Mnesia 4.6</title>
+ <section><title>Mnesia 4.7</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Returns the same value for
+ mnesia_loader:disc_load_table/2 as
+ mnesia_loader:net_load_table/4 if a table copy can not be
+ found. (Thanks to Uwe Dauernheim)</p>
+ <p>
+ Own Id: OTP-10015</p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ Improved table lock algorithm.</p>
+ <p>
+ Own Id: OTP-9890</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>Mnesia 4.6</title>
<section><title>Fixed Bugs and Malfunctions</title>
<list>
diff --git a/lib/mnesia/examples/Makefile b/lib/mnesia/examples/Makefile
index ff00ee76a5..5379761c64 100644
--- a/lib/mnesia/examples/Makefile
+++ b/lib/mnesia/examples/Makefile
@@ -78,9 +78,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) $(RELSYSDIR)/examples
- $(INSTALL_DIR) $(RELSYSDIR)/examples/bench
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) "$(RELSYSDIR)/examples"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/bench"
(cd bench; $(INSTALL_DATA) \
Makefile \
README \
@@ -96,8 +96,8 @@ release_spec: opt
bench.config5 \
bench.config6 \
bench.config7 \
- $(RELSYSDIR)/examples/bench)
- (cd bench; $(INSTALL_SCRIPT) bench.sh $(RELSYSDIR)/examples/bench)
+ "$(RELSYSDIR)/examples/bench")
+ (cd bench; $(INSTALL_SCRIPT) bench.sh "$(RELSYSDIR)/examples/bench")
release_docs_spec:
diff --git a/lib/mnesia/include/Makefile b/lib/mnesia/include/Makefile
index f9b7d72abe..20f62b5460 100644
--- a/lib/mnesia/include/Makefile
+++ b/lib/mnesia/include/Makefile
@@ -54,8 +54,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(INCLUDE_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(INCLUDE_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/mnesia/src/Makefile b/lib/mnesia/src/Makefile
index 1c8ec54605..1432eabc37 100644
--- a/lib/mnesia/src/Makefile
+++ b/lib/mnesia/src/Makefile
@@ -132,10 +132,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/mnesia/test/Makefile b/lib/mnesia/test/Makefile
index ae4c9626c7..0451da697d 100644
--- a/lib/mnesia/test/Makefile
+++ b/lib/mnesia/test/Makefile
@@ -52,24 +52,29 @@ MODULES= \
mnesia_cost \
mnesia_dbn_meters
-MnesiaExamplesDir := ../examples
+DocExamplesDir := ../doc/src/
-ExampleModules = \
+DocExampleModules = \
company \
company_o \
- bup \
- mnesia_meter \
- mnesia_tpcb
-ExamplesHrl = \
+ bup
+
+DocExamplesHrl = \
company.hrl \
company_o.hrl
-ERL_FILES= $(MODULES:%=%.erl) $(ExampleModules:%=$(MnesiaExamplesDir)/%.erl)
+ExamplesDir := ../examples/
+
+ExampleModules = \
+ mnesia_meter \
+ mnesia_tpcb
-HRL_FILES= mnesia_test_lib.hrl $(ExamplesHrl:%=$(MnesiaExamplesDir)/%)
+ERL_FILES= $(MODULES:%=%.erl) $(DocExampleModules:%=$(DocExamplesDir)/%.erl) $(ExampleModules:%=$(ExamplesDir)/%.erl)
+
+HRL_FILES= mnesia_test_lib.hrl $(DocExamplesHrl:%=$(DocExamplesDir)/%)
TARGET_FILES= \
- $(MODULES:%=$(EBIN)/%.$(EMULATOR)) $(ExampleModules:%=$(EBIN)/%.$(EMULATOR))
+ $(MODULES:%=$(EBIN)/%.$(EMULATOR)) $(DocExampleModules:%=$(EBIN)/%.$(EMULATOR)) $(ExampleModules:%=$(EBIN)/%.$(EMULATOR))
INSTALL_PROGS= $(TARGET_FILES)
@@ -91,7 +96,10 @@ EBIN = .
tests debug opt: $(TARGET_FILES)
-$(EBIN)/%.beam: $(MnesiaExamplesDir)/%.erl
+$(EBIN)/%.beam: $(DocExamplesDir)/%.erl
+ $(ERLC) -bbeam $(ERL_COMPILE_FLAGS) -o$(EBIN) $<
+
+$(EBIN)/%.beam: $(ExamplesDir)/%.erl
$(ERLC) -bbeam $(ERL_COMPILE_FLAGS) -o$(EBIN) $<
clean:
@@ -108,11 +116,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) mnesia.spec mnesia.cover $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_SCRIPT) mt $(INSTALL_PROGS) $(RELSYSDIR)
-# chmod -R u+w $(RELSYSDIR)
-# @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) mnesia.spec mnesia.cover $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_SCRIPT) mt $(INSTALL_PROGS) "$(RELSYSDIR)"
+# chmod -R u+w "$(RELSYSDIR)"
+# @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/mnesia/test/mnesia_consistency_test.erl b/lib/mnesia/test/mnesia_consistency_test.erl
index f38e13f3a2..bb21723e27 100644
--- a/lib/mnesia/test/mnesia_consistency_test.erl
+++ b/lib/mnesia/test/mnesia_consistency_test.erl
@@ -100,7 +100,7 @@ groups() ->
{group, updates_during_checkpoint_iteration},
{group, load_table_with_activated_checkpoint},
{group,
- add_table_copy_to_table_with_activated_checkpoint}]},
+ add_table_copy_to_table_checkpoint}]},
{updates_during_checkpoint_activation, [],
[updates_during_checkpoint_activation_2_ram,
updates_during_checkpoint_activation_2_disc,
@@ -116,10 +116,10 @@ groups() ->
[load_table_with_activated_checkpoint_ram,
load_table_with_activated_checkpoint_disc,
load_table_with_activated_checkpoint_disc_only]},
- {add_table_copy_to_table_with_activated_checkpoint, [],
- [add_table_copy_to_table_with_activated_checkpoint_ram,
- add_table_copy_to_table_with_activated_checkpoint_disc,
- add_table_copy_to_table_with_activated_checkpoint_disc_only]},
+ {add_table_copy_to_table_checkpoint, [],
+ [add_table_copy_to_table_checkpoint_ram,
+ add_table_copy_to_table_checkpoint_disc,
+ add_table_copy_to_table_checkpoint_disc_only]},
{backup_consistency, [],
[{group, interupted_install_fallback},
{group, interupted_uninstall_fallback},
@@ -952,16 +952,16 @@ view(Source, Mod) ->
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-add_table_copy_to_table_with_activated_checkpoint_ram(suite) -> [];
-add_table_copy_to_table_with_activated_checkpoint_ram(Config) when is_list(Config) ->
+add_table_copy_to_table_checkpoint_ram(suite) -> [];
+add_table_copy_to_table_checkpoint_ram(Config) when is_list(Config) ->
add_table_copy_to_table_with_activated_checkpoint(ram_copies, Config).
-add_table_copy_to_table_with_activated_checkpoint_disc(suite) -> [];
-add_table_copy_to_table_with_activated_checkpoint_disc(Config) when is_list(Config) ->
+add_table_copy_to_table_checkpoint_disc(suite) -> [];
+add_table_copy_to_table_checkpoint_disc(Config) when is_list(Config) ->
add_table_copy_to_table_with_activated_checkpoint(disc_copies, Config).
-add_table_copy_to_table_with_activated_checkpoint_disc_only(suite) -> [];
-add_table_copy_to_table_with_activated_checkpoint_disc_only(Config) when is_list(Config) ->
+add_table_copy_to_table_checkpoint_disc_only(suite) -> [];
+add_table_copy_to_table_checkpoint_disc_only(Config) when is_list(Config) ->
add_table_copy_to_table_with_activated_checkpoint(disc_only_copies, Config).
add_table_copy_to_table_with_activated_checkpoint(Type,Config) ->
diff --git a/lib/mnesia/vsn.mk b/lib/mnesia/vsn.mk
index 080548acac..da292cbb43 100644
--- a/lib/mnesia/vsn.mk
+++ b/lib/mnesia/vsn.mk
@@ -1 +1 @@
-MNESIA_VSN = 4.6
+MNESIA_VSN = 4.7
diff --git a/lib/observer/doc/src/Makefile b/lib/observer/doc/src/Makefile
index cd9f9466ca..0f564d3299 100644
--- a/lib/observer/doc/src/Makefile
+++ b/lib/observer/doc/src/Makefile
@@ -133,16 +133,16 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/observer/src/Makefile b/lib/observer/src/Makefile
index 91a4c656ad..7135a6abd5 100644
--- a/lib/observer/src/Makefile
+++ b/lib/observer/src/Makefile
@@ -129,20 +129,20 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_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
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_SCRIPT) $(EXECUTABLES) $(RELSYSDIR)/priv/bin
- $(INSTALL_DIR) $(RELSYSDIR)/priv/crashdump_viewer
- $(INSTALL_DATA) $(WEBTOOLFILES) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(GIF_FILES) $(RELSYSDIR)/priv/crashdump_viewer
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_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"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_SCRIPT) $(EXECUTABLES) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/crashdump_viewer"
+ $(INSTALL_DATA) $(WEBTOOLFILES) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(GIF_FILES) "$(RELSYSDIR)/priv/crashdump_viewer"
release_docs_spec:
diff --git a/lib/observer/src/crashdump_viewer_html.erl b/lib/observer/src/crashdump_viewer_html.erl
index 24a80b1916..3151b83bfb 100644
--- a/lib/observer/src/crashdump_viewer_html.erl
+++ b/lib/observer/src/crashdump_viewer_html.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2003-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2003-2012. 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
@@ -1394,7 +1394,7 @@ timers_table(Timer) ->
td("ALIGN=right",Time)]).
loaded_mods_table(#loaded_mod{mod=Mod,current_size=CS,old_size=OS}) ->
- tr([td(href(["loaded_mod_details?mod=",Mod],Mod)),
+ tr([td(href(["loaded_mod_details?mod=",http_uri:encode(Mod)],Mod)),
td("ALIGN=right",CS),
td("ALIGN=right",OS)]).
diff --git a/lib/observer/src/observer_app_wx.erl b/lib/observer/src/observer_app_wx.erl
index 7eac2b8fab..f9be11e05a 100644
--- a/lib/observer/src/observer_app_wx.erl
+++ b/lib/observer/src/observer_app_wx.erl
@@ -147,11 +147,11 @@ setup_scrollbar({CW, CH}, AppWin, #app{dim={W0,H0}}) ->
H = max(H0,CH),
PPC = 20,
if W0 =< CW, H0 =< CH ->
- wxScrolledWindow:setScrollbars(AppWin, W, H, 1, 1);
+ wxScrolledWindow:setScrollbars(AppWin, W, H, 0, 0);
H0 =< CH ->
- wxScrolledWindow:setScrollbars(AppWin, PPC, H, W div PPC+1, 1);
+ wxScrolledWindow:setScrollbars(AppWin, PPC, H, W div PPC+1, 0);
W0 =< CW ->
- wxScrolledWindow:setScrollbars(AppWin, W, PPC, 1, H div PPC+1);
+ wxScrolledWindow:setScrollbars(AppWin, W, PPC, 0, H div PPC+1);
true ->
wxScrolledWindow:setScrollbars(AppWin, PPC, PPC, W div PPC+1, H div PPC+1)
end;
@@ -204,7 +204,7 @@ handle_event(#wx{id=?ID_PROC_MSG, event=#wxCommand{type=command_menu_selected}},
handle_event(#wx{id=?ID_PROC_KILL, event=#wxCommand{type=command_menu_selected}},
State = #state{panel=Panel, sel={#box{s1=#str{pid=Pid}},_}}) ->
- case observer_lib:user_term(Panel, "Enter Exit Reason", "") of
+ case observer_lib:user_term(Panel, "Enter Exit Reason", "kill") of
cancel -> ok;
{ok, Term} -> exit(Pid, Term);
{error, Error} -> observer_lib:display_info_dialog(Error)
@@ -267,24 +267,17 @@ handle_call(Event, From, _State) ->
handle_cast(Event, _State) ->
error({unhandled_cast, Event}).
%%%%%%%%%%
-handle_info({active, Node}, State = #state{parent=Parent, current=Curr, appmon=Appmon}) ->
+handle_info({active, Node}, State = #state{parent=Parent, current=Curr}) ->
create_menus(Parent, []),
{ok, Pid} = appmon_info:start_link(Node, self(), []),
- case Appmon of
- undefined -> ok;
- Pid -> ok;
- _ -> %% Deregister me as client (and stop appmon if last)
- exit(Appmon, normal)
- end,
appmon_info:app_ctrl(Pid, Node, true, []),
(Curr =/= undefined) andalso appmon_info:app(Pid, Curr, true, []),
{noreply, State#state{appmon=Pid}};
-
-handle_info(not_active, State = #state{appmon=AppMon, current=Prev}) ->
+handle_info(not_active, State = #state{appmon=AppMon}) ->
appmon_info:app_ctrl(AppMon, node(AppMon), false, []),
- (Prev =/= undefined) andalso appmon_info:app(AppMon, Prev, false, []),
- {noreply, State};
-
+ lists:member(node(AppMon), nodes()) andalso exit(AppMon, normal),
+ observer_wx:set_status(""),
+ {noreply, State#state{appmon=undefined}};
handle_info({delivery, Pid, app_ctrl, _, Apps0},
State = #state{appmon=Pid, apps_w=LBox, current=Curr0}) ->
Apps = [atom_to_list(App) || {_, App, {_, _, _}} <- Apps0],
@@ -341,6 +334,7 @@ handle_mouse_click(Node = {#box{s1=#str{pid=Pid}},_}, Type,
right_down -> popup_menu(Panel);
_ -> ok
end,
+ observer_wx:set_status(io_lib:format("Pid: ~p", [Pid])),
wxWindow:refresh(AppWin),
State#state{sel=Node};
handle_mouse_click(_, _, State = #state{sel=undefined}) ->
@@ -349,6 +343,7 @@ handle_mouse_click(_, right_down, State=#state{panel=Panel}) ->
popup_menu(Panel),
State;
handle_mouse_click(_, _, State=#state{app_w=AppWin}) ->
+ observer_wx:set_status(""),
wxWindow:refresh(AppWin),
State#state{sel=undefined}.
@@ -376,10 +371,11 @@ popup_menu(Panel) ->
wxMenu:append(Menu, ?ID_TRACE_NAME, "Trace named process"),
wxMenu:append(Menu, ?ID_TRACE_TREE_PIDS, "Trace process tree"),
wxMenu:append(Menu, ?ID_TRACE_TREE_NAMES, "Trace named process tree"),
+ wxMenu:append(Menu, ?ID_PROC_MSG, "Send Msg"),
+ wxMenu:append(Menu, ?ID_PROC_KILL, "Kill process"),
wxWindow:popupMenu(Panel, Menu),
wxMenu:destroy(Menu).
-
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
locate_node(X, _Y, [{Box=#box{x=BX}, _Chs}|_Rest])
when X < BX ->
diff --git a/lib/observer/src/observer_pro_wx.erl b/lib/observer/src/observer_pro_wx.erl
index 7578215ff9..e2f3ddb02b 100644
--- a/lib/observer/src/observer_pro_wx.erl
+++ b/lib/observer/src/observer_pro_wx.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2011. All Rights Reserved.
+%% Copyright Ericsson AB 2011-2012. 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
@@ -191,13 +191,20 @@ dump_to_file(Parent, FileName, Holder) ->
start_procinfo(undefined, _Frame, Opened) ->
Opened;
start_procinfo(Pid, Frame, Opened) ->
- case lists:member(Pid, Opened) of
- true ->
- Opened;
- false ->
- observer_procinfo:start(Pid, Frame, self()),
- [Pid | Opened]
+ %% This code doesn't work until we collect which windows have been
+ %% closed maybe it should moved to observer_wx.erl
+ %% and add a global menu which remembers windows.
+ %% case lists:keyfind(Pid, 1, Opened) of
+ %% false ->
+ case observer_procinfo:start(Pid, Frame, self()) of
+ {error, _} -> Opened;
+ PI -> [{Pid, PI} | Opened]
end.
+ %%;
+ %% {_, PI} ->
+ %% wxFrame:raise(PI),
+ %% Opened
+ %% end.
call(Holder, What) ->
Ref = erlang:monitor(process, Holder),
diff --git a/lib/observer/src/observer_procinfo.erl b/lib/observer/src/observer_procinfo.erl
index ec08d3aff1..13e41cfe33 100644
--- a/lib/observer/src/observer_procinfo.erl
+++ b/lib/observer/src/observer_procinfo.erl
@@ -49,7 +49,8 @@ init([Pid, ParentFrame, Parent]) ->
try
Title=case observer_wx:try_rpc(node(Pid), erlang, process_info, [Pid, registered_name]) of
[] -> io_lib:format("~p",[Pid]);
- {registered_name, Registered} -> atom_to_list(Registered)
+ {registered_name, Registered} -> io_lib:format("~p (~p)",[Registered, Pid]);
+ undefined -> throw(process_undefined)
end,
Frame=wxFrame:new(ParentFrame, ?wxID_ANY, [atom_to_list(node(Pid)), $:, Title],
[{style, ?wxDEFAULT_FRAME_STYLE}, {size, {850,600}}]),
@@ -75,7 +76,10 @@ init([Pid, ParentFrame, Parent]) ->
}}
catch error:{badrpc, _} ->
observer_wx:return_to_localnode(ParentFrame, node(Pid)),
- {stop, badrpc, #state{parent=Parent, pid=Pid}}
+ {stop, badrpc};
+ process_undefined ->
+ observer_lib:display_info_dialog("No such alive process"),
+ {stop, normal}
end.
init_panel(Notebook, Str, Pid, Fun) ->
@@ -94,8 +98,11 @@ handle_event(#wx{event=#wxClose{type=close_window}}, State) ->
handle_event(#wx{id=?wxID_CLOSE, event=#wxCommand{type=command_menu_selected}}, State) ->
{stop, normal, State};
-handle_event(#wx{id=?REFRESH}, #state{pages=Pages}=State) ->
- [(W#worker.callback)() || W <- Pages],
+handle_event(#wx{id=?REFRESH}, #state{frame=Frame, pid=Pid, pages=Pages}=State) ->
+ try [(W#worker.callback)() || W <- Pages]
+ catch process_undefined ->
+ wxFrame:setTitle(Frame, io_lib:format("*DEAD* ~p",[Pid]))
+ end,
{noreply, State};
handle_event(Event, _State) ->
@@ -162,7 +169,8 @@ init_message_page(Parent, Pid) ->
false ->
wxTextCtrl:writeText(Text, Messages)
end;
- _ -> ok
+ _ ->
+ throw(process_undefined)
end
end,
Update(),
@@ -178,7 +186,8 @@ init_dict_page(Parent, Pid) ->
Last = wxTextCtrl:getLastPosition(Text),
wxTextCtrl:remove(Text, 0, Last),
wxTextCtrl:writeText(Text, Dict);
- _ -> ok
+ _ ->
+ throw(process_undefined)
end
end,
Update(),
@@ -216,7 +225,8 @@ init_stack_page(Parent, Pid) ->
wxListCtrl:setItem(LCtrl, Row, 1, FileLine),
Row+1
end, 0, RawBt);
- _ -> ok
+ _ ->
+ throw(process_undefined)
end
end,
Resize = fun(#wx{event=#wxSize{size={W,_}}},Ev) ->
@@ -266,7 +276,7 @@ process_info_fields(Pid) ->
RawInfo when is_list(RawInfo) ->
observer_lib:fill_info(Struct, RawInfo);
_ ->
- ok
+ throw(process_undefined)
end.
item_list() ->
diff --git a/lib/observer/src/observer_traceoptions_wx.erl b/lib/observer/src/observer_traceoptions_wx.erl
index 6a634e06f0..e27f565abc 100644
--- a/lib/observer/src/observer_traceoptions_wx.erl
+++ b/lib/observer/src/observer_traceoptions_wx.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2011. All Rights Reserved.
+%% Copyright Ericsson AB 2011-2012. 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
@@ -167,8 +167,10 @@ module_selector(Parent, Node) ->
function_selector(Parent, Node, Module) ->
Functions = observer_wx:try_rpc(Node, Module, module_info, [functions]),
- Choices = lists:sort([{Name, Arity} || {Name, Arity} <- Functions,
- not(erl_internal:guard_bif(Name, Arity))]),
+ Externals = observer_wx:try_rpc(Node, Module, module_info, [exports]),
+
+ Choices = lists:usort([{Name, Arity} || {Name, Arity} <- Externals ++ Functions,
+ not(erl_internal:guard_bif(Name, Arity))]),
ParsedChoices = parse_function_names(Choices),
case check_selector(Parent, ParsedChoices) of
[] -> [{Module, '_', '_'}];
diff --git a/lib/observer/src/observer_tv_table.erl b/lib/observer/src/observer_tv_table.erl
index f432173f57..3930f9ee26 100644
--- a/lib/observer/src/observer_tv_table.erl
+++ b/lib/observer/src/observer_tv_table.erl
@@ -453,7 +453,7 @@ get_attr(Table, Item) ->
Ref = erlang:monitor(process, Table),
Table ! {get_attr, self(), Item},
receive
- {'DOWN', Ref, _, _, _} -> "";
+ {'DOWN', Ref, _, _, _} -> wx:null();
{Table, Res} ->
erlang:demonitor(Ref),
Res
diff --git a/lib/observer/src/observer_wx.erl b/lib/observer/src/observer_wx.erl
index e2b256d768..ce3f48a05d 100644
--- a/lib/observer/src/observer_wx.erl
+++ b/lib/observer/src/observer_wx.erl
@@ -20,7 +20,7 @@
-behaviour(wx_object).
-export([start/0]).
--export([create_menus/2, get_attrib/1, get_tracer/0,
+-export([create_menus/2, get_attrib/1, get_tracer/0, set_status/1,
create_txt_dialog/4, try_rpc/4, return_to_localnode/2]).
-export([init/1, handle_event/2, handle_cast/2, terminate/2, code_change/3,
@@ -58,7 +58,8 @@
perf_panel,
active_tab,
node,
- nodes
+ nodes,
+ prev_node=""
}).
start() ->
@@ -73,6 +74,9 @@ create_menus(Object, Menus) when is_list(Menus) ->
get_attrib(What) ->
wx_object:call(observer, {get_attrib, What}).
+set_status(What) ->
+ wx_object:cast(observer, {status_bar, What}).
+
get_tracer() ->
wx_object:call(observer, get_tracer).
@@ -258,20 +262,21 @@ handle_event(#wx{id = ?ID_CONNECT, event = #wxCommand{type = command_menu_select
handle_event(#wx{id = ?ID_PING, event = #wxCommand{type = command_menu_selected}},
#state{frame = Frame} = State) ->
UpdState = case create_connect_dialog(ping, State) of
- cancel -> State;
+ cancel -> State;
{value, Value} when is_list(Value) ->
try
Node = list_to_atom(Value),
case net_adm:ping(Node) of
pang ->
create_txt_dialog(Frame, "Connect failed", "Pang", ?wxICON_EXCLAMATION),
- State;
+ State#state{prev_node=Value};
pong ->
- change_node_view(Node, State)
+ State1 = change_node_view(Node, State),
+ State1#state{prev_node=Value}
end
catch _:_ ->
create_txt_dialog(Frame, "Connect failed", "Pang", ?wxICON_EXCLAMATION),
- State
+ State#state{prev_node=Value}
end
end,
{noreply, UpdState};
@@ -288,6 +293,10 @@ handle_event(Event, State) ->
Pid ! Event,
{noreply, State}.
+handle_cast({status_bar, Msg}, State=#state{status_bar=SB}) ->
+ wxStatusBar:setStatusText(SB, Msg),
+ {noreply, State};
+
handle_cast(_Cast, State) ->
{noreply, State}.
@@ -439,8 +448,8 @@ pid2panel(Pid, #state{pro_panel=Pro, sys_panel=Sys,
end.
-create_connect_dialog(ping, #state{frame = Frame}) ->
- Dialog = wxTextEntryDialog:new(Frame, "Connect to node"),
+create_connect_dialog(ping, #state{frame = Frame, prev_node=Prev}) ->
+ Dialog = wxTextEntryDialog:new(Frame, "Connect to node", [{value, Prev}]),
case wxDialog:showModal(Dialog) of
?wxID_OK ->
Value = wxTextEntryDialog:getValue(Dialog),
@@ -560,7 +569,16 @@ remove_menu_items([], _MB) ->
ok.
get_nodes() ->
- Nodes = [node()| nodes()],
+ Nodes0 = case erlang:is_alive() of
+ false -> [];
+ true ->
+ case net_adm:names() of
+ {error, _} -> nodes();
+ {ok, Names} ->
+ epmd_nodes(Names) ++ nodes()
+ end
+ end,
+ Nodes = lists:usort(Nodes0),
{_, Menues} =
lists:foldl(fun(Node, {Id, Acc}) when Id < ?LAST_NODES_MENU_ID ->
{Id + 1, [#create_menu{id=Id + ?FIRST_NODES_MENU_ID,
@@ -568,6 +586,10 @@ get_nodes() ->
end, {1, []}, Nodes),
{Nodes, lists:reverse(Menues)}.
+epmd_nodes(Names) ->
+ [_, Host] = string:tokens(atom_to_list(node()),"@"),
+ [list_to_atom(Name ++ [$@|Host]) || {Name, _} <- Names].
+
update_node_list(State = #state{menubar=MenuBar}) ->
{Nodes, NodesMenuItems} = get_nodes(),
NodeMenuId = wxMenuBar:findMenu(MenuBar, "Nodes"),
diff --git a/lib/observer/test/Makefile b/lib/observer/test/Makefile
index bf99f07081..9df0591da5 100644
--- a/lib/observer/test/Makefile
+++ b/lib/observer/test/Makefile
@@ -82,11 +82,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) observer.spec $(EMAKEFILE) \
$(COVERFILE) $(ERL_FILES) \
- $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/observer/test/crashdump_viewer_SUITE.erl b/lib/observer/test/crashdump_viewer_SUITE.erl
index 5bbce9d076..6f882d0be9 100644
--- a/lib/observer/test/crashdump_viewer_SUITE.erl
+++ b/lib/observer/test/crashdump_viewer_SUITE.erl
@@ -414,6 +414,10 @@ special(Port,File) ->
_ ->
ok
end;
+ ".strangemodname" ->
+ AllMods = contents(Port,"loaded_modules"),
+ open_all_modules(Port,AllMods),
+ ok;
%%! No longer needed - all atoms are shown on one page!!
%% ".250atoms" ->
%% Html1 = contents(Port,"atoms"),
@@ -496,6 +500,26 @@ expand_binary_link(Html) ->
expand_binary_link(T)
end.
+open_all_modules(Port,Modules) ->
+ case get_first_module(Modules) of
+ {Module,Rest} ->
+ ModuleDetails = contents(Port,"loaded_mod_details?mod=" ++ Module),
+ ModTitle = http_uri:decode(Module),
+ ModTitle = title(ModuleDetails),
+ open_all_modules(Port,Rest);
+ false ->
+ ok
+ end.
+
+get_first_module([]) ->
+ false;
+get_first_module(Html) ->
+ case Html of
+ "<TD><A HREF=\"loaded_mod_details?mod=" ++ Rest ->
+ {string:sub_word(Rest,1,$"),Rest};
+ [_H|T] ->
+ get_first_module(T)
+ end.
%% next_link(Html) ->
%% case Html of
@@ -565,7 +589,7 @@ create_dumps(DataDir,[Rel|Rels],Acc) ->
Fun = fun() -> do_create_dumps(DataDir,Rel) end,
Pa = filename:dirname(code:which(?MODULE)),
{SlAllocDumps,Dumps,DosDump} =
- ?t:run_on_shielded_node(Fun, compat_rel(Rel) ++ "-pa " ++ Pa),
+ ?t:run_on_shielded_node(Fun, compat_rel(Rel) ++ "-pa \"" ++ Pa ++ "\""),
create_dumps(DataDir,Rels,SlAllocDumps ++ Dumps ++ Acc ++ DosDump);
create_dumps(_DataDir,[],Acc) ->
Acc.
@@ -590,7 +614,8 @@ do_create_dumps(DataDir,Rel) ->
case Rel of
current ->
CD3 = dump_with_args(DataDir,Rel,"instr","+Mim true"),
- {SlAllocDumps, [CD1,CD2,CD3], DosDump};
+ CD4 = dump_with_strange_module_name(DataDir,Rel,"strangemodname"),
+ {SlAllocDumps, [CD1,CD2,CD3,CD4], DosDump};
_ ->
{SlAllocDumps, [CD1,CD2], DosDump}
end.
@@ -600,7 +625,7 @@ do_create_dumps(DataDir,Rel) ->
%% not connected node, and with monitors and links between nodes.
full_dist_dump(DataDir,Rel) ->
Opt = rel_opt(Rel),
- Pz = "-pz " ++ filename:dirname(code:which(?MODULE)),
+ Pz = "-pz \"" ++ filename:dirname(code:which(?MODULE)) ++ "\"",
PzOpt = [{args,Pz}],
{ok,N1} = ?t:start_node(n1,peer,Opt ++ PzOpt),
{ok,N2} = ?t:start_node(n2,peer,Opt ++ PzOpt),
@@ -648,7 +673,22 @@ dump_with_args(DataDir,Rel,DumpName,Args) ->
?t:stop_node(n1),
CD.
+%% This dump is added to test OTP-10090 - regarding URL encoding of
+%% module names in the module detail link.
+dump_with_strange_module_name(DataDir,Rel,DumpName) ->
+ Opt = rel_opt(Rel),
+ {ok,N1} = ?t:start_node(n1,peer,Opt),
+ Mod = '<mod ule#with?strange%name>',
+ File = atom_to_list(Mod) ++ ".erl",
+ Forms = [{attribute,1,file,{File,1}},
+ {attribute,1,module,Mod},
+ {eof,4}],
+ {ok,Mod,Bin} = rpc:call(N1,compile,forms,[Forms,[binary]]),
+ {module,Mod} = rpc:call(N1,code,load_binary,[Mod,File,Bin]),
+ CD = dump(N1,DataDir,Rel,DumpName),
+ ?t:stop_node(n1),
+ CD.
dump(Node,DataDir,Rel,DumpName) ->
rpc:call(Node,erlang,halt,[DumpName]),
diff --git a/lib/observer/vsn.mk b/lib/observer/vsn.mk
index fa104ede01..4eb10ae4e8 100644
--- a/lib/observer/vsn.mk
+++ b/lib/observer/vsn.mk
@@ -1 +1 @@
-OBSERVER_VSN = 1.0
+OBSERVER_VSN = 1.1
diff --git a/lib/odbc/c_src/Makefile.in b/lib/odbc/c_src/Makefile.in
index 3a96a53ef8..5b37b352fb 100644
--- a/lib/odbc/c_src/Makefile.in
+++ b/lib/odbc/c_src/Makefile.in
@@ -128,12 +128,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
ifdef EXE_TARGET
- $(INSTALL_DIR) $(RELSYSDIR)/c_src
- $(INSTALL_DATA) $(C_FILES) $(H_FILES) $(RELSYSDIR)/c_src
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_DIR) $(RELSYSDIR)/priv/obj
- $(INSTALL_PROGRAM) $(EXE_TARGET) $(RELSYSDIR)/priv/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_src"
+ $(INSTALL_DATA) $(C_FILES) $(H_FILES) "$(RELSYSDIR)/c_src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_PROGRAM) $(EXE_TARGET) "$(RELSYSDIR)/priv/bin"
endif
release_docs_spec:
diff --git a/lib/odbc/doc/src/Makefile b/lib/odbc/doc/src/Makefile
index 0d456085f3..cd9bca0a55 100644
--- a/lib/odbc/doc/src/Makefile
+++ b/lib/odbc/doc/src/Makefile
@@ -125,13 +125,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/odbc/src/Makefile b/lib/odbc/src/Makefile
index b48dd768c8..7ca82d784b 100644
--- a/lib/odbc/src/Makefile
+++ b/lib/odbc/src/Makefile
@@ -108,13 +108,13 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXT_HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXT_HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) \
- $(RELSYSDIR)/ebin
+ "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/odbc/src/odbc.erl b/lib/odbc/src/odbc.erl
index 36afd1abcf..9f7b06dcf1 100644
--- a/lib/odbc/src/odbc.erl
+++ b/lib/odbc/src/odbc.erl
@@ -451,7 +451,7 @@ init(Args) ->
%% Start the port program (a c program) that utilizes the odbc driver
case os:find_executable(?SERVERPROG, ?SERVERDIR) of
FileName when is_list(FileName)->
- Port = open_port({spawn, FileName},
+ Port = open_port({spawn, "\""++FileName++"\""},
[{packet, ?LENGTH_INDICATOR_SIZE}, binary,
exit_status]),
State = #state{listen_sockets =
diff --git a/lib/odbc/test/Makefile b/lib/odbc/test/Makefile
index bc6449242e..84551f0eb1 100644
--- a/lib/odbc/test/Makefile
+++ b/lib/odbc/test/Makefile
@@ -101,8 +101,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(SPEC_FILES) $(COVER_FILE) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SPEC_FILES) $(COVER_FILE) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/orber/COSS/CosNaming/Makefile b/lib/orber/COSS/CosNaming/Makefile
index 064447f148..a61fcd08a6 100644
--- a/lib/orber/COSS/CosNaming/Makefile
+++ b/lib/orber/COSS/CosNaming/Makefile
@@ -141,11 +141,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/COSS/CosNaming
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(IDL_FILE) $(RELSYSDIR)/COSS/CosNaming
- $(INSTALL_DATA) $(GEN_FILES) $(RELSYSDIR)/COSS/CosNaming
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/COSS/CosNaming"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(IDL_FILE) "$(RELSYSDIR)/COSS/CosNaming"
+ $(INSTALL_DATA) $(GEN_FILES) "$(RELSYSDIR)/COSS/CosNaming"
release_docs_spec:
diff --git a/lib/orber/c_src/Makefile.in b/lib/orber/c_src/Makefile.in
index 56f0d57545..5953d41ff3 100644
--- a/lib/orber/c_src/Makefile.in
+++ b/lib/orber/c_src/Makefile.in
@@ -89,23 +89,23 @@ include $(ERL_TOP)/make/otp_release_targets.mk
ifeq ($(findstring win32,$(TARGET)),win32)
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/src
- $(INSTALL_DIR) $(RELSYSDIR)/priv/include
- $(INSTALL_PROGRAM) $(CC_FILES) $(RELSYSDIR)/priv/src
- $(INSTALL_PROGRAM) $(HH_FILES) $(RELSYSDIR)/priv/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/include"
+ $(INSTALL_PROGRAM) $(CC_FILES) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_PROGRAM) $(HH_FILES) "$(RELSYSDIR)/priv/include"
else
ifeq ($(findstring vxworks,$(TARGET)),vxworks)
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/priv/src
- $(INSTALL_DIR) $(RELSYSDIR)/priv/include
- $(INSTALL_PROGRAM) $(CC_FILES) $(RELSYSDIR)/priv/src
- $(INSTALL_PROGRAM) $(HH_FILES) $(RELSYSDIR)/priv/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/include"
+ $(INSTALL_PROGRAM) $(CC_FILES) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_PROGRAM) $(HH_FILES) "$(RELSYSDIR)/priv/include"
else
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/src
- $(INSTALL_DIR) $(RELSYSDIR)/priv/include
- $(INSTALL_DATA) $(CC_FILES) $(RELSYSDIR)/priv/src
- $(INSTALL_DATA) $(HH_FILES) $(RELSYSDIR)/priv/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/include"
+ $(INSTALL_DATA) $(CC_FILES) "$(RELSYSDIR)/priv/src"
+ $(INSTALL_DATA) $(HH_FILES) "$(RELSYSDIR)/priv/include"
endif
endif
diff --git a/lib/orber/doc/src/Makefile b/lib/orber/doc/src/Makefile
index 68fbe3dce0..c429c1d80b 100644
--- a/lib/orber/doc/src/Makefile
+++ b/lib/orber/doc/src/Makefile
@@ -164,13 +164,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/orber/doc/src/notes.xml b/lib/orber/doc/src/notes.xml
index 35ee5e35dd..72cd808d20 100644
--- a/lib/orber/doc/src/notes.xml
+++ b/lib/orber/doc/src/notes.xml
@@ -32,7 +32,29 @@
<file>notes.xml</file>
</header>
- <section><title>Orber 3.6.23</title>
+ <section><title>Orber 3.6.24</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Fix number of arguments in orber dbg printout</p>
+ <p>
+ Own Id: OTP-9887</p>
+ </item>
+ <item>
+ <p> The descriptions of <c>ssl_server_options</c> and
+ <c>ssl_client_options</c> are corrected.<br/> Seq. Id:
+ seq12018 </p>
+ <p>
+ Own Id: OTP-9966 Aux Id: OTP-9773 </p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>Orber 3.6.23</title>
<section><title>Fixed Bugs and Malfunctions</title>
<list>
diff --git a/lib/orber/examples/Stack/Makefile b/lib/orber/examples/Stack/Makefile
index b985f348fa..b03d7c3b86 100644
--- a/lib/orber/examples/Stack/Makefile
+++ b/lib/orber/examples/Stack/Makefile
@@ -118,8 +118,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/Stack
- $(INSTALL_DATA) $(ERL_FILES) $(JAVA_FILES) $(CPP_FILES) $(IDL_FILES) $(RELSYSDIR)/examples/Stack
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/Stack"
+ $(INSTALL_DATA) $(ERL_FILES) $(JAVA_FILES) $(CPP_FILES) $(IDL_FILES) "$(RELSYSDIR)/examples/Stack"
release_docs_spec:
diff --git a/lib/orber/java_src/Orber/Makefile b/lib/orber/java_src/Orber/Makefile
index 49da975a8b..4e52ed3635 100644
--- a/lib/orber/java_src/Orber/Makefile
+++ b/lib/orber/java_src/Orber/Makefile
@@ -63,8 +63,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/java_src/Orber
- $(INSTALL_DATA) $(JAVA_FILES) $(RELSYSDIR)/java_src/Orber
+ $(INSTALL_DIR) "$(RELSYSDIR)/java_src/Orber"
+ $(INSTALL_DATA) $(JAVA_FILES) "$(RELSYSDIR)/java_src/Orber"
release_docs_spec:
diff --git a/lib/orber/priv/Makefile b/lib/orber/priv/Makefile
index af82177466..7957f7bbf0 100644
--- a/lib/orber/priv/Makefile
+++ b/lib/orber/priv/Makefile
@@ -58,8 +58,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(HELP_FILES) $(HTML_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(HELP_FILES) $(HTML_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/orber/src/Makefile b/lib/orber/src/Makefile
index d2e98686da..a57d6d948b 100644
--- a/lib/orber/src/Makefile
+++ b/lib/orber/src/Makefile
@@ -254,12 +254,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(GEN_HRL_FILES_LOC) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(GEN_HRL_FILES_EXT) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(GEN_HRL_FILES_LOC) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXTERNAL_HRL_FILES) $(GEN_HRL_FILES_EXT) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/orber/test/Makefile b/lib/orber/test/Makefile
index d4be009af3..8eef1934a4 100644
--- a/lib/orber/test/Makefile
+++ b/lib/orber/test/Makefile
@@ -209,12 +209,12 @@ release_spec:
release_docs_spec:
release_tests_spec: tests
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(IDL_FILES) $(TEST_SPEC_FILE) $(COVER_FILE) \
- $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_TARGET_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- $(INSTALL_DIR) $(RELSYSDIR)/$(IDLOUTDIR)
+ $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_TARGET_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELSYSDIR)/$(IDLOUTDIR)"
$(INSTALL_DATA) $(GEN_TARGET_FILES) $(GEN_FILES) \
- $(RELSYSDIR)/$(IDLOUTDIR)
+ "$(RELSYSDIR)/$(IDLOUTDIR)"
diff --git a/lib/orber/test/orber_test_lib.erl b/lib/orber/test/orber_test_lib.erl
index 0ddde49cd6..2bfa1ef871 100644
--- a/lib/orber/test/orber_test_lib.erl
+++ b/lib/orber/test/orber_test_lib.erl
@@ -282,6 +282,7 @@ starter(Host, Name, Args) ->
vxworks ->
test_server:start_node(Name, slave, [{args,Args}]);
_ ->
+ io:format("slave:start_link(~p,~p,~p).~n",[Host,Name,Args]),
slave:start_link(Host, Name, Args)
end.
@@ -403,8 +404,8 @@ create_paths() ->
filename:join(Path, "idl_output") ++
" -pa " ++
filename:join(Path, "all_SUITE_data") ++
- " -pa " ++
- filename:dirname(code:which(orber)).
+ " -pa \"" ++
+ filename:dirname(code:which(orber))++"\"".
%%------------------------------------------------------------
%% function : destroy_node
diff --git a/lib/orber/vsn.mk b/lib/orber/vsn.mk
index 0eac1e1410..f891440600 100644
--- a/lib/orber/vsn.mk
+++ b/lib/orber/vsn.mk
@@ -1,3 +1,3 @@
-ORBER_VSN = 3.6.23
+ORBER_VSN = 3.6.24
diff --git a/lib/os_mon/c_src/Makefile.in b/lib/os_mon/c_src/Makefile.in
index bac0413ece..45dc01e993 100644
--- a/lib/os_mon/c_src/Makefile.in
+++ b/lib/os_mon/c_src/Makefile.in
@@ -131,10 +131,10 @@ ifeq ($(findstring vxworks_simso,$(TARGET)),vxworks_simso)
release_spec:
else
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(C_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_PROGRAM) $(TARGET_FILES) $(RELSYSDIR)/priv/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(C_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_PROGRAM) $(TARGET_FILES) "$(RELSYSDIR)/priv/bin"
endif
release_docs_spec:
diff --git a/lib/os_mon/doc/src/Makefile b/lib/os_mon/doc/src/Makefile
index c9765749c9..aa8fb4b60c 100644
--- a/lib/os_mon/doc/src/Makefile
+++ b/lib/os_mon/doc/src/Makefile
@@ -109,16 +109,16 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/os_mon/doc/src/notes.xml b/lib/os_mon/doc/src/notes.xml
index b459e31fa5..6674d7b722 100644
--- a/lib/os_mon/doc/src/notes.xml
+++ b/lib/os_mon/doc/src/notes.xml
@@ -30,6 +30,25 @@
</header>
<p>This document describes the changes made to the OS_Mon application.</p>
+<section><title>Os_Mon 2.2.9</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Fix segmentation fault in memsup</p>
+ <p>
+ when /proc/meminfo does not include information about
+ buffers/cache (for instance inside OpenVZ container)
+ (Thanks to Anton Vorobev)</p>
+ <p>
+ Own Id: OTP-9913</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Os_Mon 2.2.8</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/os_mon/mibs/Makefile b/lib/os_mon/mibs/Makefile
index 655190edf4..a6d8ab5042 100644
--- a/lib/os_mon/mibs/Makefile
+++ b/lib/os_mon/mibs/Makefile
@@ -88,13 +88,13 @@ $(SNMP_BIN_TARGET_DIR)/OTP-OS-MON-MIB.bin: \
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/mibs
- $(INSTALL_DIR) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DATA) $(MIB_FILES) $(FUNCS_FILES) $(RELSYSDIR)/mibs
- $(INSTALL_DATA) $(V1_MIB_FILES) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_TARGETS) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/priv/mibs
- $(INSTALL_DATA) $(BIN_TARGETS) $(RELSYSDIR)/priv/mibs
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DATA) $(MIB_FILES) $(FUNCS_FILES) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DATA) $(V1_MIB_FILES) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_TARGETS) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/mibs"
+ $(INSTALL_DATA) $(BIN_TARGETS) "$(RELSYSDIR)/priv/mibs"
release_docs_spec:
diff --git a/lib/os_mon/src/Makefile b/lib/os_mon/src/Makefile
index 9a75446a89..a8ad26f6a1 100644
--- a/lib/os_mon/src/Makefile
+++ b/lib/os_mon/src/Makefile
@@ -94,11 +94,11 @@ $(EBIN)/memsup.$(EMULATOR): $(MEMSUP_HRL)
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/os_mon/src/disksup.erl b/lib/os_mon/src/disksup.erl
index 308cd1b7fa..c7abb7a386 100644
--- a/lib/os_mon/src/disksup.erl
+++ b/lib/os_mon/src/disksup.erl
@@ -43,24 +43,24 @@ start_link() ->
gen_server:start_link({local, disksup}, disksup, [], []).
get_disk_data() ->
- os_mon:call(disksup, get_disk_data).
+ os_mon:call(disksup, get_disk_data, infinity).
get_check_interval() ->
- os_mon:call(disksup, get_check_interval).
+ os_mon:call(disksup, get_check_interval, infinity).
set_check_interval(Minutes) ->
case param_type(disk_space_check_interval, Minutes) of
true ->
- os_mon:call(disksup, {set_check_interval, Minutes});
+ os_mon:call(disksup, {set_check_interval, Minutes}, infinity);
false ->
erlang:error(badarg)
end.
get_almost_full_threshold() ->
- os_mon:call(disksup, get_almost_full_threshold).
+ os_mon:call(disksup, get_almost_full_threshold, infinity).
set_almost_full_threshold(Float) ->
case param_type(disk_almost_full_threshold, Float) of
true ->
- os_mon:call(disksup, {set_almost_full_threshold, Float});
+ os_mon:call(disksup, {set_almost_full_threshold, Float}, infinity);
false ->
erlang:error(badarg)
end.
diff --git a/lib/os_mon/src/memsup.erl b/lib/os_mon/src/memsup.erl
index 5ef240f128..54771b4703 100644
--- a/lib/os_mon/src/memsup.erl
+++ b/lib/os_mon/src/memsup.erl
@@ -112,7 +112,7 @@ get_helper_timeout() ->
set_helper_timeout(Seconds) ->
case param_type(memsup_helper_timeout, Seconds) of
true ->
- os_mon:call(memsup, {set_helper_timeout, Seconds});
+ os_mon:call(memsup, {set_helper_timeout, Seconds}, infinity);
false ->
erlang:error(badarg)
end.
diff --git a/lib/os_mon/src/os_mon.erl b/lib/os_mon/src/os_mon.erl
index 3098c38808..2b6cd7c498 100644
--- a/lib/os_mon/src/os_mon.erl
+++ b/lib/os_mon/src/os_mon.erl
@@ -85,13 +85,13 @@ open_port(Name, Opts) ->
%% Check os_mon*/priv/bin/Name
case filelib:is_regular(ReleasedPath) of
true ->
- erlang:open_port({spawn, ReleasedPath}, Opts);
+ erlang:open_port({spawn, "\""++ReleasedPath++"\""}, Opts);
false ->
%% Use os_mon*/priv/bin/Arch/Name
ArchPath =
filename:join(
[PrivDir,"bin",erlang:system_info(system_architecture),Name]),
- erlang:open_port({spawn, ArchPath}, Opts)
+ erlang:open_port({spawn, "\""++ArchPath++"\""}, Opts)
end.
diff --git a/lib/os_mon/test/Makefile b/lib/os_mon/test/Makefile
index a240640f92..954cfef7fb 100644
--- a/lib/os_mon/test/Makefile
+++ b/lib/os_mon/test/Makefile
@@ -84,9 +84,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) os_mon.spec os_mon.cover $(EMAKEFILE) $(SOURCE) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) os_mon.spec os_mon.cover $(EMAKEFILE) $(SOURCE) "$(RELSYSDIR)"
-## tar chf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+## tar chf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/os_mon/vsn.mk b/lib/os_mon/vsn.mk
index 89dfa59dd9..b92bdf3c1a 100644
--- a/lib/os_mon/vsn.mk
+++ b/lib/os_mon/vsn.mk
@@ -1 +1 @@
-OS_MON_VSN = 2.2.8
+OS_MON_VSN = 2.2.9
diff --git a/lib/otp_mibs/doc/src/Makefile b/lib/otp_mibs/doc/src/Makefile
index bd2810034b..16a5bb39b4 100644
--- a/lib/otp_mibs/doc/src/Makefile
+++ b/lib/otp_mibs/doc/src/Makefile
@@ -102,14 +102,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/otp_mibs/mibs/Makefile b/lib/otp_mibs/mibs/Makefile
index 5e59824d3f..7ef8480b3e 100644
--- a/lib/otp_mibs/mibs/Makefile
+++ b/lib/otp_mibs/mibs/Makefile
@@ -76,13 +76,13 @@ v1/%.mib.v1: %.mib
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/mibs
- $(INSTALL_DIR) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DATA) $(MIB_FILES) $(FUNCS_FILES) $(RELSYSDIR)/mibs
- $(INSTALL_DATA) $(V1_MIB_FILES) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_TARGETS) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/priv/mibs
- $(INSTALL_DATA) $(BIN_TARGETS) $(RELSYSDIR)/priv/mibs
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DATA) $(MIB_FILES) $(FUNCS_FILES) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DATA) $(V1_MIB_FILES) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_TARGETS) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/mibs"
+ $(INSTALL_DATA) $(BIN_TARGETS) "$(RELSYSDIR)/priv/mibs"
release_docs_spec:
diff --git a/lib/otp_mibs/src/Makefile b/lib/otp_mibs/src/Makefile
index 833a439adb..c9c40fec3a 100644
--- a/lib/otp_mibs/src/Makefile
+++ b/lib/otp_mibs/src/Makefile
@@ -95,10 +95,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGETS) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGETS) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/parsetools/doc/src/Makefile b/lib/parsetools/doc/src/Makefile
index 6e693e0cf0..464ea66af0 100644
--- a/lib/parsetools/doc/src/Makefile
+++ b/lib/parsetools/doc/src/Makefile
@@ -105,14 +105,14 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/parsetools/src/Makefile b/lib/parsetools/src/Makefile
index 89e079e411..e228ee88ef 100644
--- a/lib/parsetools/src/Makefile
+++ b/lib/parsetools/src/Makefile
@@ -89,12 +89,12 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/parsetools/test/Makefile b/lib/parsetools/test/Makefile
index 624c4e6975..430386bfe5 100644
--- a/lib/parsetools/test/Makefile
+++ b/lib/parsetools/test/Makefile
@@ -70,9 +70,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) parsetools.spec parsetools.cover $(EMAKEFILE) $(ERL_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- # @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) parsetools.spec parsetools.cover $(EMAKEFILE) $(ERL_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ # @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/percept/doc/src/Makefile b/lib/percept/doc/src/Makefile
index f0d43c5a01..e749103783 100644
--- a/lib/percept/doc/src/Makefile
+++ b/lib/percept/doc/src/Makefile
@@ -175,15 +175,15 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTML_EXAMPLE_FILES) $(HTML_STYLESHEET_FILES) \
$(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/percept/priv/Makefile b/lib/percept/priv/Makefile
index 7c37ccd98b..4d7942c49c 100644
--- a/lib/percept/priv/Makefile
+++ b/lib/percept/priv/Makefile
@@ -77,20 +77,20 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
# Finished
- $(INSTALL_DIR) $(RELSYSDIR)/priv/logs
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root/htdocs
- $(INSTALL_DATA) $(HTDOCS_FILES) $(RELSYSDIR)/priv/server_root/htdocs
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root/conf
- $(INSTALL_DATA) $(CONF_FILES) $(RELSYSDIR)/priv/server_root/conf
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root/scripts
- $(INSTALL_DATA) $(SCRIPT_FILES) $(RELSYSDIR)/priv/server_root/scripts
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root/css
- $(INSTALL_DATA) $(CSS_FILES) $(RELSYSDIR)/priv/server_root/css
- $(INSTALL_DIR) $(RELSYSDIR)/priv/server_root/images
- $(INSTALL_DATA) $(IMAGE_FILES) $(RELSYSDIR)/priv/server_root/images
- $(INSTALL_DIR) $(RELSYSDIR)/priv/fonts
- $(INSTALL_DATA) $(FONT_FILES) $(RELSYSDIR)/priv/fonts
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/logs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root/htdocs"
+ $(INSTALL_DATA) $(HTDOCS_FILES) "$(RELSYSDIR)/priv/server_root/htdocs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root/conf"
+ $(INSTALL_DATA) $(CONF_FILES) "$(RELSYSDIR)/priv/server_root/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root/scripts"
+ $(INSTALL_DATA) $(SCRIPT_FILES) "$(RELSYSDIR)/priv/server_root/scripts"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root/css"
+ $(INSTALL_DATA) $(CSS_FILES) "$(RELSYSDIR)/priv/server_root/css"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/server_root/images"
+ $(INSTALL_DATA) $(IMAGE_FILES) "$(RELSYSDIR)/priv/server_root/images"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/fonts"
+ $(INSTALL_DATA) $(FONT_FILES) "$(RELSYSDIR)/priv/fonts"
release_docs_spec:
diff --git a/lib/percept/src/Makefile b/lib/percept/src/Makefile
index 5dfc72575a..4b9a10cdb8 100644
--- a/lib/percept/src/Makefile
+++ b/lib/percept/src/Makefile
@@ -93,12 +93,12 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
-# $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+# $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/percept/test/Makefile b/lib/percept/test/Makefile
index d927386d1c..ee70966b01 100644
--- a/lib/percept/test/Makefile
+++ b/lib/percept/test/Makefile
@@ -81,10 +81,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) percept.spec percept.cover $(EMAKEFILE) $(SOURCE) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) percept.spec percept.cover $(EMAKEFILE) $(SOURCE) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/pman/doc/src/Makefile b/lib/pman/doc/src/Makefile
index 4e116cb23e..ec759091ab 100644
--- a/lib/pman/doc/src/Makefile
+++ b/lib/pman/doc/src/Makefile
@@ -103,14 +103,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/pman/doc/src/notes.xml b/lib/pman/doc/src/notes.xml
index 82cb35af00..778f960004 100644
--- a/lib/pman/doc/src/notes.xml
+++ b/lib/pman/doc/src/notes.xml
@@ -30,6 +30,26 @@
</header>
<p>This document describes the changes made to the Pman application.</p>
+<section><title>Pman 2.7.1.2</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Pman 2.7.1.1</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/pman/priv/Makefile b/lib/pman/priv/Makefile
index 43f9d45d94..a89278fd3a 100644
--- a/lib/pman/priv/Makefile
+++ b/lib/pman/priv/Makefile
@@ -50,8 +50,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(TOOLBAR_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(TOOLBAR_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/pman/src/Makefile b/lib/pman/src/Makefile
index e573e57220..2cd1c64c49 100644
--- a/lib/pman/src/Makefile
+++ b/lib/pman/src/Makefile
@@ -103,10 +103,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(TOOLBOX_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(TARGET_TOOLBOX_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(TOOLBOX_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(TARGET_TOOLBOX_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/pman/vsn.mk b/lib/pman/vsn.mk
index a62a9d7c89..13dce1a7a5 100644
--- a/lib/pman/vsn.mk
+++ b/lib/pman/vsn.mk
@@ -1 +1 @@
-PMAN_VSN = 2.7.1.1
+PMAN_VSN = 2.7.1.2
diff --git a/lib/public_key/asn1/Makefile b/lib/public_key/asn1/Makefile
index 943d97bdb8..d48f48a5d5 100644
--- a/lib/public_key/asn1/Makefile
+++ b/lib/public_key/asn1/Makefile
@@ -91,13 +91,13 @@ $(INCLUDE)/%.hrl: %.hrl
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/asn1
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/asn1"
$(INSTALL_DATA) $(ASN_ASNS) $(ASN_ERLS) $(ASN_HRLS) $(ASN_CONFIGS) \
- $(GEN_ERLS) $(RELSYSDIR)/asn1
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(GEN_ERLS) "$(RELSYSDIR)/asn1"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/public_key/doc/src/Makefile b/lib/public_key/doc/src/Makefile
index 9616a96195..928aa62c1b 100644
--- a/lib/public_key/doc/src/Makefile
+++ b/lib/public_key/doc/src/Makefile
@@ -114,14 +114,14 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
info:
diff --git a/lib/public_key/doc/src/notes.xml b/lib/public_key/doc/src/notes.xml
index c9a5561e3f..4d3a9856eb 100644
--- a/lib/public_key/doc/src/notes.xml
+++ b/lib/public_key/doc/src/notes.xml
@@ -34,6 +34,35 @@
<file>notes.xml</file>
</header>
+<section><title>Public_Key 0.15</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ Changed ssh implementation to use the public_key
+ application for all public key handling. This is also a
+ first step for enabling a callback API for supplying
+ public keys and handling keys protected with password
+ phrases. </p>
+ <p>
+ Additionally the test suites where improved so that they
+ do not copy the users keys to test server directories as
+ this is a security liability. Also ipv6 and file access
+ issues found in the process has been fixed.</p>
+ <p>
+ This change also solves OTP-7677 and OTP-7235</p>
+ <p>
+ This changes also involves some updates to public_keys
+ ssh-functions.</p>
+ <p>
+ Own Id: OTP-9911</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Public_Key 0.14</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/public_key/src/Makefile b/lib/public_key/src/Makefile
index 062c495a65..8a72da477f 100644
--- a/lib/public_key/src/Makefile
+++ b/lib/public_key/src/Makefile
@@ -102,11 +102,11 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/public_key/src/public_key.erl b/lib/public_key/src/public_key.erl
index 2e2a6cd296..9f1a0b3af5 100644
--- a/lib/public_key/src/public_key.erl
+++ b/lib/public_key/src/public_key.erl
@@ -241,15 +241,15 @@ pkix_encode(Asn1Type, Term0, otp) when is_atom(Asn1Type) ->
decrypt_private(CipherText, Key) ->
decrypt_private(CipherText, Key, []).
-decrypt_private(CipherText,
- #'RSAPrivateKey'{modulus = N,publicExponent = E,
- privateExponent = D},
- Options) when is_binary(CipherText),
- is_list(Options) ->
+decrypt_private(CipherText,
+ #'RSAPrivateKey'{modulus = N, publicExponent = E,
+ privateExponent = D} = Key,
+ Options)
+ when is_binary(CipherText),
+ is_integer(N), is_integer(E), is_integer(D),
+ is_list(Options) ->
Padding = proplists:get_value(rsa_pad, Options, rsa_pkcs1_padding),
- crypto:rsa_private_decrypt(CipherText,
- [crypto:mpint(E), crypto:mpint(N),
- crypto:mpint(D)], Padding).
+ crypto:rsa_private_decrypt(CipherText, format_rsa_private_key(Key), Padding).
%%--------------------------------------------------------------------
-spec decrypt_public(CipherText :: binary(), rsa_public_key() | rsa_private_key()) ->
@@ -307,14 +307,29 @@ encrypt_public(PlainText, #'RSAPrivateKey'{modulus=N,publicExponent=E},
encrypt_private(PlainText, Key) ->
encrypt_private(PlainText, Key, []).
-encrypt_private(PlainText, #'RSAPrivateKey'{modulus = N,
- publicExponent = E,
- privateExponent = D},
- Options) when is_binary(PlainText), is_list(Options) ->
+encrypt_private(PlainText,
+ #'RSAPrivateKey'{modulus = N, publicExponent = E,
+ privateExponent = D} = Key,
+ Options)
+ when is_binary(PlainText),
+ is_integer(N), is_integer(E), is_integer(D),
+ is_list(Options) ->
Padding = proplists:get_value(rsa_pad, Options, rsa_pkcs1_padding),
- crypto:rsa_private_encrypt(PlainText, [crypto:mpint(E),
- crypto:mpint(N),
- crypto:mpint(D)], Padding).
+ crypto:rsa_private_encrypt(PlainText, format_rsa_private_key(Key), Padding).
+
+
+format_rsa_private_key(#'RSAPrivateKey'{modulus = N, publicExponent = E,
+ privateExponent = D,
+ prime1 = P1, prime2 = P2,
+ exponent1 = E1, exponent2 = E2,
+ coefficient = C})
+ when is_integer(P1), is_integer(P2),
+ is_integer(E1), is_integer(E2), is_integer(C) ->
+ [crypto:mpint(K) || K <- [E, N, D, P1, P2, E1, E2, C]];
+
+format_rsa_private_key(#'RSAPrivateKey'{modulus = N, publicExponent = E,
+ privateExponent = D}) ->
+ [crypto:mpint(K) || K <- [E, N, D]].
%%--------------------------------------------------------------------
-spec sign(PlainTextOrDigest :: binary(), rsa_digest_type() | dss_digest_type(),
@@ -323,15 +338,13 @@ encrypt_private(PlainText, #'RSAPrivateKey'{modulus = N,
%%
%% Description: Create digital signature.
%%--------------------------------------------------------------------
-sign(PlainText, DigestType, #'RSAPrivateKey'{modulus = N, publicExponent = E,
- privateExponent = D})
+sign(PlainText, DigestType,
+ #'RSAPrivateKey'{modulus = N, publicExponent = E, privateExponent = D} = Key)
when is_binary(PlainText),
- (DigestType == md5 orelse
- DigestType == sha) ->
-
- crypto:rsa_sign(DigestType, sized_binary(PlainText), [crypto:mpint(E),
- crypto:mpint(N),
- crypto:mpint(D)]);
+ (DigestType == md5 orelse DigestType == sha),
+ is_integer(N), is_integer(E), is_integer(D) ->
+ crypto:rsa_sign(DigestType, sized_binary(PlainText),
+ format_rsa_private_key(Key));
sign(Digest, none, #'DSAPrivateKey'{p = P, q = Q, g = G, x = X})
when is_binary(Digest)->
diff --git a/lib/public_key/test/Makefile b/lib/public_key/test/Makefile
index b7f91981a5..41d77f103b 100644
--- a/lib/public_key/test/Makefile
+++ b/lib/public_key/test/Makefile
@@ -21,7 +21,7 @@ include $(ERL_TOP)/make/target.mk
include $(ERL_TOP)/make/$(TARGET)/otp.mk
-INCLUDES= -I. -I ../include
+INCLUDES= -I. -I ../include -pa $(ERL_TOP)/lib/public_key/ebin
# ----------------------------------------------------
# Target Specs
@@ -78,11 +78,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(SPEC_FILES) $(ERL_FILES) $(COVER_FILE) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SPEC_FILES) $(ERL_FILES) $(COVER_FILE) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/reltool/doc/src/Makefile b/lib/reltool/doc/src/Makefile
index 8bc1488f77..0b85b7e02c 100644
--- a/lib/reltool/doc/src/Makefile
+++ b/lib/reltool/doc/src/Makefile
@@ -97,13 +97,13 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(HTMLDIR)/* $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(HTMLDIR)/* "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/reltool/doc/src/notes.xml b/lib/reltool/doc/src/notes.xml
index cf2cf7f7bc..0aae128c2b 100644
--- a/lib/reltool/doc/src/notes.xml
+++ b/lib/reltool/doc/src/notes.xml
@@ -37,7 +37,149 @@
thus constitutes one section in this document. The title of each
section is the version number of Reltool.</p>
- <section><title>Reltool 0.5.7.1</title>
+ <section><title>Reltool 0.6</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Miscellaneous corrections: <list> <item> Start of reltool
+ GUI would sometimes crash with a badmatch in
+ reltool_sys_win:do_init. This has been corrected. </item>
+ <item> Minor corrections of documentation and type
+ specifications of app() and mod() are done. </item>
+ <item> If a module name is duplicated in an app file
+ reltool would return an error. This is now changed to a
+ warning. </item> <item> Reltool would earlier not
+ necessarily keep the order of applications as listed in
+ the rel specification in the configuration. This has been
+ corrected. </item> <item> Reltool would earlier set the
+ default for included applications to an empty list if it
+ was not set in the rel specification in the
+ configuration. This was correct according to
+ sasl/systools documentation, but not according to
+ sasl/systools implementation. We decided to change the
+ documentation and reltool to use the value of
+ included_applications from the .app file as default
+ instead of the empty list, since this seems more
+ intuitive and since systools always has done the same.
+ </item> <item> The value of included applications in the
+ rel specification in the configuration did not overwrite
+ included_applications in the .app file if it was set to
+ an empty list. This has been corrected. </item> <item>
+ Reltool would earlier add load instructions in the
+ script/boot files for ALL modules in the ebin directory
+ of an application even if mod_cond was set to app
+ (include only modules listed in the .app file). This has
+ been corrected. </item> <item> Reltool would earlier add
+ start instructions in the script/boot file for included
+ applications. This has been corrected - included
+ applications shall only be loaded since the including
+ application is responsible for starting them. </item>
+ <item> Status bar now indicates that reltool is working
+ (Processing libraries...) for all configuration changes,
+ and when generating target system. </item> <item> Title
+ of dependecies column in app and mod window is changed
+ from "Modules used by others" to "Modules using this".
+ </item> </list></p>
+ <p>
+ Own Id: OTP-9792</p>
+ </item>
+ <item>
+ <p>
+ Configuration changes via the GUI had a few bugs related
+ to error handling, rollback and undo. A major re-write of
+ the reltool_server has been done in order to align the
+ way reltool_server updates and uses its state and tables
+ for all different kinds of configuration change. </p>
+ <p>
+ All configuration changes (except undo) now cause a
+ re-read of the file system, meaning that if something has
+ changed in the file system it will be reflected in the
+ result of the configuration change.</p>
+ <p>
+ When loading a new configuration file via the GUI, the
+ old configuration is now completely scratched, and only
+ the new is valid.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9794</p>
+ </item>
+ <item>
+ <p>
+ Some bug fixes related to the handling of escripts:
+ <list> <item> Reltool could not handle escripts with
+ inlined applications. This has been corrected. Inlined
+ applications will be visible in the GUI, but not possible
+ to include/exclude separately. </item> <item> Loading a
+ config which contains an escript via the GUI menu did not
+ produce the same result as when using the same
+ configuration at reltool start. Paths, version and label
+ could differ. This has been corrected. </item> <item>
+ Loading config with same escript (source) twice caused
+ reltool to add same module twice. This has been
+ corrected. </item> <item> Loading config with same
+ escript (inlined beam) twice caused reltool to fail
+ saying module is included by two different applications.
+ This has been corrected. </item> <item> Loading config
+ which in addition to an existing escript also adds
+ another escript, for which the name sorts before the
+ existing one, would cause reltool to fail saying
+ "Application name clash". This has been corrected.
+ </item> </list></p>
+ <p>
+ Own Id: OTP-9968</p>
+ </item>
+ <item>
+ <p>
+ Reltool would sometimes generate a .app file containing
+ <c>{start_phases,undefined}</c>, which would cause an
+ exception in systools at parse time. This has been
+ corrected so reltool now omits the <c>start_phases</c>
+ entry if the value is <c>undefined</c>. (Thanks to Juan
+ Jose Comellas)</p>
+ <p>
+ In order to align with reltool, sasl will also omit
+ <c>start_phases</c> entries with value <c>undefined</c>
+ in .script files.</p>
+ <p>
+ Own Id: OTP-10003</p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ A warning list is added to the sys window of the reltool
+ GUI. This list will continuously show all warnings
+ produced by the current configuration.</p>
+ <p>
+ Own Id: OTP-9967</p>
+ </item>
+ <item>
+ <p>
+ As a way of specifying one specific version of an
+ application, the following configuration parameter is
+ added on application level:</p>
+ <p>
+ {lib_dir,Dir}, Dir = string()</p>
+ <p>
+ This can be useful if the parent directory of the
+ application directory is not suitable to use as a lib dir
+ on system level.</p>
+ <p>
+ Own Id: OTP-9977</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>Reltool 0.5.7.1</title>
<section><title>Improvements and New Features</title>
<list>
diff --git a/lib/reltool/examples/Makefile b/lib/reltool/examples/Makefile
index dacfd4e7d4..afc47e1d12 100644
--- a/lib/reltool/examples/Makefile
+++ b/lib/reltool/examples/Makefile
@@ -72,8 +72,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(ERL_FILES) $(DATA_FILES) $(HRL_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/reltool/src/Makefile b/lib/reltool/src/Makefile
index 4e6a112b7e..4730b4acff 100644
--- a/lib/reltool/src/Makefile
+++ b/lib/reltool/src/Makefile
@@ -97,11 +97,11 @@ $(TARGET_FILES): $(HRL_FILES) $(INTERNAL_HRL_FILES)
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/reltool/test/Makefile b/lib/reltool/test/Makefile
index d8a7adb837..52cdef44da 100644
--- a/lib/reltool/test/Makefile
+++ b/lib/reltool/test/Makefile
@@ -49,7 +49,7 @@ RELSYSDIR = $(RELEASE_PATH)/reltool_test
# ----------------------------------------------------
# FLAGS
# ----------------------------------------------------
-#ERL_COMPILE_FLAGS +=
+ERL_COMPILE_FLAGS += -pa $(ERL_TOP)/lib/reltool/ebin/
EBIN = .
@@ -73,12 +73,12 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) reltool.spec reltool.cover $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_SCRIPT) rtt $(INSTALL_PROGS) $(RELSYSDIR)
- $(INSTALL_DATA) $(INSTALL_PROGS) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) reltool.spec reltool.cover $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_SCRIPT) rtt $(INSTALL_PROGS) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(INSTALL_PROGS) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/reltool/vsn.mk b/lib/reltool/vsn.mk
index 3869284ee7..3811d897c7 100644
--- a/lib/reltool/vsn.mk
+++ b/lib/reltool/vsn.mk
@@ -1 +1 @@
-RELTOOL_VSN = 0.5.7.1
+RELTOOL_VSN = 0.6
diff --git a/lib/runtime_tools/c_src/Makefile.in b/lib/runtime_tools/c_src/Makefile.in
index cbbcfa2d56..754e6ccd78 100644
--- a/lib/runtime_tools/c_src/Makefile.in
+++ b/lib/runtime_tools/c_src/Makefile.in
@@ -193,10 +193,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/obj
- $(INSTALL_DIR) $(RELSYSDIR)/priv/lib
- $(INSTALL_PROGRAM) $(DYNTRACE_OBJS) $(RELSYSDIR)/priv/obj
- $(INSTALL_PROGRAM) $(NIF_LIB) $(SOLIBS) $(RELSYSDIR)/priv/lib
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/lib"
+ $(INSTALL_PROGRAM) $(DYNTRACE_OBJS) "$(RELSYSDIR)/priv/obj"
+ $(INSTALL_PROGRAM) $(NIF_LIB) $(SOLIBS) "$(RELSYSDIR)/priv/lib"
release_docs_spec:
diff --git a/lib/runtime_tools/doc/src/Makefile b/lib/runtime_tools/doc/src/Makefile
index c67f7bd1f6..d240b287c3 100644
--- a/lib/runtime_tools/doc/src/Makefile
+++ b/lib/runtime_tools/doc/src/Makefile
@@ -108,16 +108,16 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/runtime_tools/doc/src/notes.xml b/lib/runtime_tools/doc/src/notes.xml
index ccf11bf0fe..2d4a206e1c 100644
--- a/lib/runtime_tools/doc/src/notes.xml
+++ b/lib/runtime_tools/doc/src/notes.xml
@@ -31,6 +31,28 @@
<p>This document describes the changes made to the Runtime_Tools
application.</p>
+<section><title>Runtime_Tools 1.8.8</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ The DTrace source patch from Scott Lystig Fritchie is
+ integrated in the source tree. Using an emulator with
+ dtrace probe is still not supported for production use,
+ but may be a valuable debugging tool. Configure with
+ --with-dynamic-trace=dtrace (or
+ --with-dynamic-trace=systemtap) to create a build with
+ dtrace probes enabled. See runtime_tools for
+ documentation and examples.</p>
+ <p>
+ Own Id: OTP-10017</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Runtime_Tools 1.8.7</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/runtime_tools/src/Makefile b/lib/runtime_tools/src/Makefile
index cb302b79c2..810e3e8741 100644
--- a/lib/runtime_tools/src/Makefile
+++ b/lib/runtime_tools/src/Makefile
@@ -99,14 +99,14 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/examples
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(EXAMPLE_FILES) "$(RELSYSDIR)/examples"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/runtime_tools/test/Makefile b/lib/runtime_tools/test/Makefile
index 3e50ba02ca..4979b9c7b1 100644
--- a/lib/runtime_tools/test/Makefile
+++ b/lib/runtime_tools/test/Makefile
@@ -57,10 +57,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) runtime_tools.spec runtime_tools.cover $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(EMAKEFILE) runtime_tools.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) runtime_tools.spec runtime_tools.cover $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EMAKEFILE) runtime_tools.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/runtime_tools/vsn.mk b/lib/runtime_tools/vsn.mk
index 3fbc1b3379..c9b5cc1a41 100644
--- a/lib/runtime_tools/vsn.mk
+++ b/lib/runtime_tools/vsn.mk
@@ -1 +1 @@
-RUNTIME_TOOLS_VSN = 1.8.7
+RUNTIME_TOOLS_VSN = 1.8.8
diff --git a/lib/sasl/doc/src/Makefile b/lib/sasl/doc/src/Makefile
index eb880ccb78..b0ec671adc 100644
--- a/lib/sasl/doc/src/Makefile
+++ b/lib/sasl/doc/src/Makefile
@@ -116,18 +116,18 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man4
- $(INSTALL_DATA) $(MAN4_FILES) $(RELEASE_PATH)/man/man4
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man4"
+ $(INSTALL_DATA) $(MAN4_FILES) "$(RELEASE_PATH)/man/man4"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/sasl/doc/src/notes.xml b/lib/sasl/doc/src/notes.xml
index 2f22a8ec43..e4a2c98db7 100644
--- a/lib/sasl/doc/src/notes.xml
+++ b/lib/sasl/doc/src/notes.xml
@@ -30,6 +30,102 @@
</header>
<p>This document describes the changes made to the SASL application.</p>
+<section><title>SASL 2.2.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ If sys.config existed, but was not readable or parseable,
+ this would not be detected until after the upgrade and at
+ the next node restart. The possibility for this to happen
+ is now reduced by adding a check to systools:make_tar
+ which fails the creation of the tar file if sys.config or
+ relup does not have reasonable contents. Note that there
+ are no detailed checks, only parsing and erlang term
+ format check.</p>
+ <p>
+ Own Id: OTP-9539</p>
+ </item>
+ <item>
+ <p>
+ systools:make_script would allow {kernel,Vsn,load} in the
+ .rel file, causing a .boot file which only loaded kernel
+ and did not start it. This has been corrected. Only start
+ type 'permanent', which is the default, is now allowed
+ for kernel and stdlib.</p>
+ <p>
+ Own Id: OTP-9652</p>
+ </item>
+ <item>
+ <p>
+ release_handler:remove_release/1 now handles symlinked
+ files properly</p>
+ <p>
+ Own Id: OTP-9864</p>
+ </item>
+ <item>
+ <p>
+ If stdlib was stated with a start type different from
+ <c>permanent</c> in a .rel file, systools would
+ incorrectly say that sasl had faulty start type. This has
+ been corrected.</p>
+ <p>
+ Own Id: OTP-9888</p>
+ </item>
+ <item>
+ <p>
+ Sasl documentation earlier said that the InclApps
+ parameters in a .rel file defaults to the empty list.
+ This is not correct. It defaults to the same value as
+ specified in the .app file. This has been corrected.</p>
+ <p>
+ Own Id: OTP-9980</p>
+ </item>
+ <item>
+ <p>
+ Applications that are listed in
+ <c>{applications,Apps}</c> in the .app file were not
+ sorted correctly by <c>systools:make_script/1,2</c>. They
+ got the reverse order of how they were listed in the .app
+ file. This is corrected so they are now sorted
+ (internally between each other) in the same order as they
+ are listed in the .rel file (i.e. the order they are
+ listed in the .app file does no longer matter).</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9984</p>
+ </item>
+ <item>
+ <p>
+ Documentation of .appup files now also states that
+ <c>UpFromVsn</c> and <c>DownToVsn</c> can be specified as
+ regular expressions in order to avoid duplicated upgrade
+ instructions.</p>
+ <p>
+ Own Id: OTP-10001</p>
+ </item>
+ <item>
+ <p>
+ Reltool would sometimes generate a .app file containing
+ <c>{start_phases,undefined}</c>, which would cause an
+ exception in systools at parse time. This has been
+ corrected so reltool now omits the <c>start_phases</c>
+ entry if the value is <c>undefined</c>. (Thanks to Juan
+ Jose Comellas)</p>
+ <p>
+ In order to align with reltool, sasl will also omit
+ <c>start_phases</c> entries with value <c>undefined</c>
+ in .script files.</p>
+ <p>
+ Own Id: OTP-10003</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>SASL 2.2</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/sasl/examples/src/Makefile b/lib/sasl/examples/src/Makefile
index 9cf0d4c25d..47c8626205 100644
--- a/lib/sasl/examples/src/Makefile
+++ b/lib/sasl/examples/src/Makefile
@@ -63,10 +63,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/src
- $(INSTALL_DIR) $(RELSYSDIR)/examples/ebin
- (cd ..; tar cf - src ebin | (cd $(RELSYSDIR)/examples; tar xf -))
- chmod -R ug+w $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/ebin"
+ (cd ..; tar cf - src ebin | (cd "$(RELSYSDIR)/examples"; tar xf -))
+ chmod -R ug+w "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/sasl/src/Makefile b/lib/sasl/src/Makefile
index 9a5d1e42d9..cae8146ebc 100644
--- a/lib/sasl/src/Makefile
+++ b/lib/sasl/src/Makefile
@@ -91,10 +91,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/sasl/test/Makefile b/lib/sasl/test/Makefile
index 91a8c42484..bb3f82f411 100644
--- a/lib/sasl/test/Makefile
+++ b/lib/sasl/test/Makefile
@@ -85,10 +85,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) sasl.spec sasl.cover $(EMAKEFILE) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cfh - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) sasl.spec sasl.cover $(EMAKEFILE) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cfh - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/sasl/vsn.mk b/lib/sasl/vsn.mk
index 23694f1399..6e9e2c9ff8 100644
--- a/lib/sasl/vsn.mk
+++ b/lib/sasl/vsn.mk
@@ -1 +1 @@
-SASL_VSN = 2.2
+SASL_VSN = 2.2.1
diff --git a/lib/snmp/doc/src/Makefile b/lib/snmp/doc/src/Makefile
index 8645886590..6c58ae994a 100644
--- a/lib/snmp/doc/src/Makefile
+++ b/lib/snmp/doc/src/Makefile
@@ -170,20 +170,20 @@ $(MAN1DIR)/snmpc.1: snmpc_cmd.xml
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man1
- $(INSTALL_DATA) $(MAN1DIR)/* $(RELEASE_PATH)/man/man1
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6DIR)/* $(RELEASE_PATH)/man/man6
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man7
- $(INSTALL_DATA) $(MAN7DIR)/* $(RELEASE_PATH)/man/man7
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DATA) $(MAN1DIR)/* "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6DIR)/* "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man7"
+ $(INSTALL_DATA) $(MAN7DIR)/* "$(RELEASE_PATH)/man/man7"
release_spec:
diff --git a/lib/snmp/examples/ex1/Makefile b/lib/snmp/examples/ex1/Makefile
index 1a55ba0470..996b686e0e 100644
--- a/lib/snmp/examples/ex1/Makefile
+++ b/lib/snmp/examples/ex1/Makefile
@@ -46,7 +46,7 @@ ERL_COMPILE_FLAGS += -I../include \
# Release directory specification
# ----------------------------------------------------
RELSYSDIR = $(RELEASE_PATH)/lib/snmp-$(VSN)
-EXAMPLE_RELSYSDIR = $(RELSYSDIR)/examples
+EXAMPLE_RELSYSDIR = "$(RELSYSDIR)/examples"
EX1_RELSYSDIR = $(EXAMPLE_RELSYSDIR)/ex1
# ----------------------------------------------------
diff --git a/lib/snmp/examples/ex2/Makefile b/lib/snmp/examples/ex2/Makefile
index 7fbd7f530b..090b9274d4 100644
--- a/lib/snmp/examples/ex2/Makefile
+++ b/lib/snmp/examples/ex2/Makefile
@@ -47,7 +47,7 @@ ERL_COMPILE_FLAGS += -I../include \
# Release directory specification
# ----------------------------------------------------
RELSYSDIR = $(RELEASE_PATH)/lib/snmp-$(VSN)
-EXAMPLE_RELSYSDIR = $(RELSYSDIR)/examples
+EXAMPLE_RELSYSDIR = "$(RELSYSDIR)/examples"
EX2_RELSYSDIR = $(EXAMPLE_RELSYSDIR)/ex2
# ----------------------------------------------------
diff --git a/lib/snmp/mibs/Makefile.in b/lib/snmp/mibs/Makefile.in
index 993a67c6f2..c74c0b2ac4 100644
--- a/lib/snmp/mibs/Makefile.in
+++ b/lib/snmp/mibs/Makefile.in
@@ -211,7 +211,7 @@ info:
@echo ""
@echo "SNMP_VSN = $(SNMP_VSN)"
@echo "VSN = $(VSN)"
- @echo "RELSYSDIR = $(RELSYSDIR)"
+ @echo "RELSYSDIR = "$(RELSYSDIR)""
v1/%.mib.v1: %.mib $(ERL_TOP)/lib/snmp/bin/snmp-v2tov1
$(ERL_TOP)/lib/snmp/bin/snmp-v2tov1 -o $@ $<
@@ -223,17 +223,17 @@ v1/%.mib.v1: %.mib $(ERL_TOP)/lib/snmp/bin/snmp-v2tov1
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/mibs
- $(INSTALL_DIR) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DATA) $(MIB_FILES) $(RELSYSDIR)/mibs
- $(INSTALL_DATA) $(STD_v2_MIB_FILES) $(RELSYSDIR)/mibs
- $(INSTALL_DATA) $(FUNCS_FILES) $(RELSYSDIR)/mibs
- $(INSTALL_DATA) $(STD_v1_MIB_FILES) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DATA) $(V1_MIB_FILES) $(RELSYSDIR)/mibs/v1
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/priv/mibs
- $(INSTALL_DATA) $(BIN_TARGETS) $(RELSYSDIR)/priv/mibs
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DIR) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DATA) $(MIB_FILES) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DATA) $(STD_v2_MIB_FILES) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DATA) $(FUNCS_FILES) "$(RELSYSDIR)/mibs"
+ $(INSTALL_DATA) $(STD_v1_MIB_FILES) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DATA) $(V1_MIB_FILES) "$(RELSYSDIR)/mibs/v1"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/mibs"
+ $(INSTALL_DATA) $(BIN_TARGETS) "$(RELSYSDIR)/priv/mibs"
release_docs_spec:
diff --git a/lib/snmp/priv/conf/agent/Makefile b/lib/snmp/priv/conf/agent/Makefile
index ee3a915c2b..c7921bacc2 100644
--- a/lib/snmp/priv/conf/agent/Makefile
+++ b/lib/snmp/priv/conf/agent/Makefile
@@ -55,9 +55,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/conf
- $(INSTALL_DIR) $(RELSYSDIR)/priv/conf/agent
- $(INSTALL_DATA) $(CONF_FILES) $(RELSYSDIR)/priv/conf/agent
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/conf/agent"
+ $(INSTALL_DATA) $(CONF_FILES) "$(RELSYSDIR)/priv/conf/agent"
release_docs_spec:
diff --git a/lib/snmp/priv/conf/manager/Makefile b/lib/snmp/priv/conf/manager/Makefile
index 16355f0ff3..ba5a74c3fe 100644
--- a/lib/snmp/priv/conf/manager/Makefile
+++ b/lib/snmp/priv/conf/manager/Makefile
@@ -55,9 +55,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv/conf
- $(INSTALL_DIR) $(RELSYSDIR)/priv/conf/manager
- $(INSTALL_DATA) $(CONF_FILES) $(RELSYSDIR)/priv/conf/manager
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/conf/manager"
+ $(INSTALL_DATA) $(CONF_FILES) "$(RELSYSDIR)/priv/conf/manager"
release_docs_spec:
diff --git a/lib/snmp/src/agent/Makefile b/lib/snmp/src/agent/Makefile
index a67fe4d17c..9a982edf91 100644
--- a/lib/snmp/src/agent/Makefile
+++ b/lib/snmp/src/agent/Makefile
@@ -128,14 +128,14 @@ info:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/agent
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src/agent
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/agent"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src/agent"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) \
- $(RELSYSDIR)/ebin
-# $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(EXT_HRL_FILES) $(RELSYSDIR)/include
+ "$(RELSYSDIR)/ebin"
+# $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(EXT_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/snmp/src/app/Makefile b/lib/snmp/src/app/Makefile
index d89eb4e723..7a16d42c30 100644
--- a/lib/snmp/src/app/Makefile
+++ b/lib/snmp/src/app/Makefile
@@ -127,14 +127,14 @@ $(APPUP_TARGET): $(APPUP_SRC) ../../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/app
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src/app
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/app"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src/app"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) \
- $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXT_HRL_FILES) $(RELSYSDIR)/include
+ "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXT_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/snmp/src/compile/Makefile b/lib/snmp/src/compile/Makefile
index 627af6f185..9658ee0005 100644
--- a/lib/snmp/src/compile/Makefile
+++ b/lib/snmp/src/compile/Makefile
@@ -120,13 +120,13 @@ $(GENERATED_PARSER): $(PARSER_SRC)
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/compiler
- $(INSTALL_DATA) $(ESCRIPT_SRC) $(PARSER_SRC) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src/compiler
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(EBIN_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/bin
- $(INSTALL_SCRIPT) $(ESCRIPT_BIN) $(RELSYSDIR)/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/compiler"
+ $(INSTALL_DATA) $(ESCRIPT_SRC) $(PARSER_SRC) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src/compiler"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(EBIN_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/bin"
+ $(INSTALL_SCRIPT) $(ESCRIPT_BIN) "$(RELSYSDIR)/bin"
release_docs_spec:
diff --git a/lib/snmp/src/manager/Makefile b/lib/snmp/src/manager/Makefile
index c1d5703300..1f30669f02 100644
--- a/lib/snmp/src/manager/Makefile
+++ b/lib/snmp/src/manager/Makefile
@@ -111,13 +111,13 @@ info:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/manager
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src/manager
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
-# $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(EXT_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/manager"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src/manager"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+# $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(EXT_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/snmp/src/misc/Makefile b/lib/snmp/src/misc/Makefile
index 48d76bdbed..c6a5064d89 100644
--- a/lib/snmp/src/misc/Makefile
+++ b/lib/snmp/src/misc/Makefile
@@ -109,13 +109,13 @@ info:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/misc
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src/misc
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
-# $(INSTALL_DIR) $(RELSYSDIR)/include
-# $(INSTALL_DATA) $(EXT_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/misc"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src/misc"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+# $(INSTALL_DIR) "$(RELSYSDIR)/include"
+# $(INSTALL_DATA) $(EXT_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/snmp/test/Makefile b/lib/snmp/test/Makefile
index 40a294f783..546d46a002 100644
--- a/lib/snmp/test/Makefile
+++ b/lib/snmp/test/Makefile
@@ -79,7 +79,7 @@ COVER_SPEC_FILE = snmp.cover
# ----------------------------------------------------
# Release directory specification
# ----------------------------------------------------
-RELSYSDIR = $(RELEASE_PATH)/snmp_test
+RELSYSDIR = $(RELEASE_PATH)/snmp_test
# ----------------------------------------------------
@@ -235,10 +235,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(RELTEST_FILES) $(COVER_SPEC_FILE) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- tar cf - snmp_test_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(RELTEST_FILES) $(COVER_SPEC_FILE) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ tar cf - snmp_test_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
@@ -254,7 +254,7 @@ info:
@echo ""
@echo "ERL_COMPILE_FLAGS = $(ERL_COMPILE_FLAGS)"
@echo ""
- @echo "RELSYSDIR = $(RELSYSDIR)"
+ @echo "RELSYSDIR = "$(RELSYSDIR)""
@echo ""
@echo "SOURCE = $(SOURCE)"
@echo ""
diff --git a/lib/ssh/doc/src/Makefile b/lib/ssh/doc/src/Makefile
index 125dcf8775..38782a3b00 100644
--- a/lib/ssh/doc/src/Makefile
+++ b/lib/ssh/doc/src/Makefile
@@ -109,13 +109,13 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/ssh/doc/src/notes.xml b/lib/ssh/doc/src/notes.xml
index c6c634212f..a85cada732 100644
--- a/lib/ssh/doc/src/notes.xml
+++ b/lib/ssh/doc/src/notes.xml
@@ -29,6 +29,108 @@
<file>notes.xml</file>
</header>
+<section><title>Ssh 2.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ All keys in authorized_keys are considerd, wrongly only
+ the first one was before.</p>
+ <p>
+ Own Id: OTP-7235</p>
+ </item>
+ <item>
+ <p>
+ ssh daemon now properly handles ras host keys, in
+ previous versions only dsa host keys sufficed to set up a
+ connection.</p>
+ <p>
+ Own Id: OTP-7677</p>
+ </item>
+ <item>
+ <p>
+ ssh:shell/3 and ssh:connect/3 does not hang anymore if
+ connection negotiation fails</p>
+ <p>
+ Own Id: OTP-8111</p>
+ </item>
+ <item>
+ <p>
+ Improve check so that we will not try to read ssh packet
+ length indicator if not sure we have enough data.</p>
+ <p>
+ Own Id: OTP-8380</p>
+ </item>
+ <item>
+ <p>
+ Do not try to use user interaction when it is disabled.</p>
+ <p>
+ Own Id: OTP-9466 Aux Id: seq11886 </p>
+ </item>
+ <item>
+ <p>
+ Improved error handling of internal errors i the ssh
+ connection handling process</p>
+ <p>
+ Own Id: OTP-9905</p>
+ </item>
+ <item>
+ <p>
+ sftp daemon generates file handles correct</p>
+ <p>
+ Own Id: OTP-9948</p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ Document supported algorithms</p>
+ <p>
+ Own Id: OTP-8109</p>
+ </item>
+ <item>
+ <p>
+ Graceful handling of premature close from an sftp client.</p>
+ <p>
+ Own Id: OTP-9391 Aux Id: seq11838 </p>
+ </item>
+ <item>
+ <p>
+ Changed ssh implementation to use the public_key
+ application for all public key handling. This is also a
+ first step for enabling a callback API for supplying
+ public keys and handling keys protected with password
+ phrases. </p>
+ <p>
+ Additionally the test suites where improved so that they
+ do not copy the users keys to test server directories as
+ this is a security liability. Also ipv6 and file access
+ issues found in the process has been fixed.</p>
+ <p>
+ This change also solves OTP-7677 and OTP-7235</p>
+ <p>
+ This changes also involves some updates to public_keys
+ ssh-functions.</p>
+ <p>
+ Own Id: OTP-9911</p>
+ </item>
+ <item>
+ <p>
+ Added options for the ssh client to support user keys
+ files that are password protected.</p>
+ <p>
+ Own Id: OTP-10036 Aux Id: OTP-6400, Seq10595 </p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Ssh 2.0.9</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/ssh/examples/Makefile b/lib/ssh/examples/Makefile
index 5f17542fb8..84c7edac8c 100644
--- a/lib/ssh/examples/Makefile
+++ b/lib/ssh/examples/Makefile
@@ -69,8 +69,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/ssh/src/Makefile b/lib/ssh/src/Makefile
index 1734ae4df4..b8eecd3fa2 100644
--- a/lib/ssh/src/Makefile
+++ b/lib/ssh/src/Makefile
@@ -38,15 +38,17 @@ RELSYSDIR = $(RELEASE_PATH)/lib/ssh-$(VSN)
# Behaviour (api) modules are first so they are compiled when
# the compiler reaches a callback module using them.
-MODULES= \
+BEHAVIOUR_MODULES= \
ssh_sftpd_file_api \
- ssh_key_api \
+ ssh_channel \
+ ssh_key_api
+
+MODULES= \
ssh \
ssh_sup \
sshc_sup \
sshd_sup \
ssh_connection_sup \
- ssh_channel \
ssh_connection \
ssh_connection_handler \
ssh_connection_manager \
@@ -73,11 +75,14 @@ MODULES= \
PUBLIC_HRL_FILES= ssh.hrl ssh_userauth.hrl ssh_xfer.hrl
-ERL_FILES= $(MODULES:%=%.erl)
+ERL_FILES= \
+ $(MODULES:%=%.erl) \
+ $(BEHAVIOUR_MODULES:%=%.erl)
-ALL_MODULES= $(MODULES)
-TARGET_FILES= $(ALL_MODULES:%=$(EBIN)/%.$(EMULATOR)) $(APP_TARGET) $(APPUP_TARGET)
+TARGET_FILES= $(MODULES:%=$(EBIN)/%.$(EMULATOR))
+
+BEHAVIOUR_TARGET_FILES= $(BEHAVIOUR_MODULES:%=$(EBIN)/%.$(EMULATOR))
APP_FILE= ssh.app
APPUP_FILE= ssh.appup
@@ -93,29 +98,29 @@ INTERNAL_HRL_FILES = ssh_auth.hrl ssh_connect.hrl ssh_transport.hrl
# ----------------------------------------------------
# FLAGS
# ----------------------------------------------------
-ERL_COMPILE_FLAGS += -pa$(EBIN)\
- -pz $(ERL_TOP)/lib/public_key/ebin
+EXTRA_ERLC_FLAGS = +warn_unused_vars
+ERL_COMPILE_FLAGS += -I$(ERL_TOP)/lib/kernel/src \
+ -pz $(EBIN) \
+ -pz $(ERL_TOP)/lib/public_key/ebin \
+ $(EXTRA_ERLC_FLAGS)
+
+
# ----------------------------------------------------
# Targets
# ----------------------------------------------------
-debug opt: $(TARGET_FILES)
+$(TARGET_FILES): $(BEHAVIOUR_TARGET_FILES)
-debug: ERLC_FLAGS += -Ddebug
+debug opt: $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
clean:
- rm -f $(TARGET_FILES)
+ rm -f $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
rm -f errs core *~
-$(TARGET_FILES): ssh.hrl
-
-# $(EBIN)/ssh_sftpd_file.$(EMULATOR): ERLC_FLAGS += -pa$(EBIN)
-# $(EBIN)/ssh_sftpd_file.$(EMULATOR): $(EBIN)/ssh_sftpd_file_api.$(EMULATOR)
-
-$(APP_TARGET): $(APP_SRC) ../vsn.mk
+$(APP_TARGET): $(APP_SRC) ../vsn.mk
sed -e 's;%VSN%;$(VSN);' $< > $@
-$(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
+$(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
sed -e 's;%VSN%;$(VSN);' $< > $@
@@ -127,12 +132,13 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(PUBLIC_HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(BEHAVIOUR_TARGET_FILES) $(TARGET_FILES) $(APP_TARGET) \
+ $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(PUBLIC_HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/ssh/src/ssh.erl b/lib/ssh/src/ssh.erl
index 39c7fe329e..f4a40c81a4 100644
--- a/lib/ssh/src/ssh.erl
+++ b/lib/ssh/src/ssh.erl
@@ -346,8 +346,9 @@ handle_option([{role, _} = Opt | Rest], SocketOptions, SshOptions) ->
handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
handle_option([{compression, _} = Opt | Rest], SocketOptions, SshOptions) ->
handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
-handle_option([{allow_user_interaction, _} = Opt | Rest], SocketOptions, SshOptions) ->
- handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
+%%Backwards compatibility
+handle_option([{allow_user_interaction, Value} | Rest], SocketOptions, SshOptions) ->
+ handle_option(Rest, SocketOptions, [handle_ssh_option({user_interaction, Value}) | SshOptions]);
handle_option([{infofun, _} = Opt | Rest],SocketOptions, SshOptions) ->
handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
handle_option([{connectfun, _} = Opt | Rest], SocketOptions, SshOptions) ->
@@ -366,6 +367,8 @@ handle_option([{ssh_cli, _} = Opt | Rest], SocketOptions, SshOptions) ->
handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
handle_option([{shell, _} = Opt | Rest], SocketOptions, SshOptions) ->
handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
+handle_option([{exec, _} = Opt | Rest], SocketOptions, SshOptions) ->
+ handle_option(Rest, SocketOptions, [handle_ssh_option(Opt) | SshOptions]);
handle_option([Opt | Rest], SocketOptions, SshOptions) ->
handle_option(Rest, [handle_inet_option(Opt) | SocketOptions], SshOptions).
@@ -401,8 +404,9 @@ handle_ssh_option({key_cb, Value} = Opt) when is_atom(Value) ->
Opt;
handle_ssh_option({compression, Value} = Opt) when is_atom(Value) ->
Opt;
-handle_ssh_option({allow_user_interaction, Value} = Opt) when Value == true;
- Value == false ->
+handle_ssh_option({exec, {Module, Function, _}} = Opt) when is_atom(Module),
+ is_atom(Function) ->
+
Opt;
handle_ssh_option({infofun, Value} = Opt) when is_function(Value) ->
Opt;
@@ -412,11 +416,12 @@ handle_ssh_option({disconnectfun , Value} = Opt) when is_function(Value) ->
Opt;
handle_ssh_option({failfun, Value} = Opt) when is_function(Value) ->
Opt;
-handle_ssh_option({ip_v6_disabled, Value} = Opt) when is_function(Value) ->
+handle_ssh_option({ip_v6_disabled, Value} = Opt) when Value == true;
+ Value == false ->
Opt;
handle_ssh_option({transport, {Protocol, Cb, ClosTag}} = Opt) when is_atom(Protocol),
- is_atom(Cb),
- is_atom(ClosTag) ->
+ is_atom(Cb),
+ is_atom(ClosTag) ->
Opt;
handle_ssh_option({subsystems, Value} = Opt) when is_list(Value) ->
Opt;
@@ -495,4 +500,3 @@ verify_data(Data, Signature, Algorithm) when is_binary(Data), is_binary(Signatur
Error ->
Error
end.
-
diff --git a/lib/ssh/src/ssh_auth.erl b/lib/ssh/src/ssh_auth.erl
index 1a4517c689..aa452a8e09 100644
--- a/lib/ssh/src/ssh_auth.erl
+++ b/lib/ssh/src/ssh_auth.erl
@@ -71,7 +71,7 @@ password_msg([#ssh{opts = Opts, io_cb = IoCb,
ssh_bits:install_messages(userauth_passwd_messages()),
Password = case proplists:get_value(password, Opts) of
undefined ->
- user_interaction(Opts, IoCb);
+ user_interaction(IoCb);
PW ->
PW
end,
@@ -89,13 +89,10 @@ password_msg([#ssh{opts = Opts, io_cb = IoCb,
Ssh)
end.
-user_interaction(Opts, IoCb) ->
- case proplists:get_value(allow_user_interaction, Opts, true) of
- true ->
- IoCb:read_password("ssh password: ");
- false ->
- not_ok
- end.
+user_interaction(ssh_no_io) ->
+ not_ok;
+user_interaction(IoCb) ->
+ IoCb:read_password("ssh password: ").
%% See RFC 4256 for info on keyboard-interactive
@@ -124,8 +121,7 @@ init_userauth_request_msg(#ssh{opts = Opts} = Ssh) ->
FirstAlg = algorithm(proplists:get_value(public_key_alg, Opts,
?PREFERRED_PK_ALG)),
SecondAlg = other_alg(FirstAlg),
- AllowUserInt = proplists:get_value(allow_user_interaction, Opts,
- true),
+ AllowUserInt = proplists:get_value(user_interaction, Opts, true),
Prefs = method_preference(FirstAlg, SecondAlg, AllowUserInt),
ssh_transport:ssh_packet(Msg, Ssh#ssh{user = User,
userauth_preference = Prefs,
diff --git a/lib/ssh/src/ssh_channel.erl b/lib/ssh/src/ssh_channel.erl
index 7b600ed8b2..1938858420 100644
--- a/lib/ssh/src/ssh_channel.erl
+++ b/lib/ssh/src/ssh_channel.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2008-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2008-2012. 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
@@ -215,7 +215,7 @@ handle_info({ssh_cm, ConnectionManager, {closed, ChannelId}},
close_sent = false} = State) ->
%% To be on the safe side, i.e. the manager has already been terminated.
(catch ssh_connection:close(ConnectionManager, ChannelId)),
- {stop, normal, State};
+ {stop, normal, State#state{close_sent = true}};
handle_info({ssh_cm, _, _} = Msg, #state{cm = ConnectionManager,
channel_cb = Module,
diff --git a/lib/ssh/src/ssh_connection.erl b/lib/ssh/src/ssh_connection.erl
index 46f0c7e688..c46f799b6d 100644
--- a/lib/ssh/src/ssh_connection.erl
+++ b/lib/ssh/src/ssh_connection.erl
@@ -720,12 +720,17 @@ handle_msg(#ssh_msg_channel_request{request_type = "env"},
handle_msg(#ssh_msg_channel_request{recipient_channel = ChannelId,
request_type = _Other,
- want_reply = WantReply}, Connection,
+ want_reply = WantReply}, #connection{channel_cache = Cache} = Connection,
ConnectionPid, _) ->
if WantReply == true ->
- FailMsg = channel_failure_msg(ChannelId),
- {{replies, [{connection_reply, ConnectionPid, FailMsg}]},
- Connection};
+ case ssh_channel:cache_lookup(Cache, ChannelId) of
+ #channel{remote_id = RemoteId} ->
+ FailMsg = channel_failure_msg(RemoteId),
+ {{replies, [{connection_reply, ConnectionPid, FailMsg}]},
+ Connection};
+ undefined -> %% Chanel has been closed
+ {noreply, Connection}
+ end;
true ->
{noreply, Connection}
end;
diff --git a/lib/ssh/src/ssh_connection_manager.erl b/lib/ssh/src/ssh_connection_manager.erl
index e993f597a5..e53cd4f4f7 100644
--- a/lib/ssh/src/ssh_connection_manager.erl
+++ b/lib/ssh/src/ssh_connection_manager.erl
@@ -267,7 +267,7 @@ handle_call({ssh_msg, Pid, Msg}, From,
disconnect_fun(Reason, SSHOpts),
{stop, {shutdown, normal}, State#state{connection_state = Connection}}
catch
- _:Reason ->
+ _:Error ->
{disconnect, Reason, {{replies, Replies}, Connection}} =
ssh_connection:handle_msg(
#ssh_msg_disconnect{code = ?SSH_DISCONNECT_BY_APPLICATION,
@@ -277,7 +277,7 @@ handle_call({ssh_msg, Pid, Msg}, From,
lists:foreach(fun send_msg/1, Replies),
SSHOpts = proplists:get_value(ssh_opts, Opts),
disconnect_fun(Reason, SSHOpts),
- {stop, {shutdown, Reason}, State#state{connection_state = Connection}}
+ {stop, {shutdown, Error}, State#state{connection_state = Connection}}
end;
handle_call({global_request, Pid, _, _, _} = Request, From,
@@ -384,9 +384,10 @@ handle_call({close, ChannelId}, _,
#state{connection = Pid, connection_state =
#connection{channel_cache = Cache}} = State) ->
case ssh_channel:cache_lookup(Cache, ChannelId) of
- #channel{remote_id = Id} ->
+ #channel{remote_id = Id} = Channel ->
send_msg({connection_reply, Pid,
ssh_connection:channel_close_msg(Id)}),
+ ssh_channel:cache_update(Cache, Channel#channel{sent_close = true}),
{reply, ok, State};
undefined ->
{reply, ok, State}
@@ -585,7 +586,7 @@ call(Pid, Msg, Timeout) ->
catch
exit:{timeout, _} ->
{error, timeout};
- exit:{normal} ->
+ exit:{normal, _} ->
{error, channel_closed};
exit:{{shutdown, _}, _} ->
{error, channel_closed};
diff --git a/lib/ssh/test/Makefile b/lib/ssh/test/Makefile
index 145d5d2ad6..25072688ad 100644
--- a/lib/ssh/test/Makefile
+++ b/lib/ssh/test/Makefile
@@ -110,11 +110,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) ssh.spec ssh.cover $(RELSYSDIR)
- $(INSTALL_DATA) $(HRL_FILES_NEEDED_IN_TEST) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) ssh.spec ssh.cover "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(HRL_FILES_NEEDED_IN_TEST) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/ssh/test/ssh_basic_SUITE.erl b/lib/ssh/test/ssh_basic_SUITE.erl
index d66214d415..c5019425cd 100644
--- a/lib/ssh/test/ssh_basic_SUITE.erl
+++ b/lib/ssh/test/ssh_basic_SUITE.erl
@@ -183,7 +183,29 @@ app_test(doc) ->
app_test(Config) when is_list(Config) ->
?t:app_test(ssh),
ok.
+%%--------------------------------------------------------------------
+misc_ssh_options(doc) ->
+ ["Test that we can set some misc options not tested elsewhere, "
+ "some options not yet present are not decided if we should support or "
+ "if they need thier own test case."];
+misc_ssh_options(suite) ->
+ [];
+misc_ssh_options(Config) when is_list(Config) ->
+ SystemDir = filename:join(?config(priv_dir, Config), system),
+ UserDir = ?config(priv_dir, Config),
+
+ CMiscOpt0 = [{connecect_timeout, 1000}, {ip_v6_disable, false}, {user_dir, UserDir}],
+ CMiscOpt1 = [{connecect_timeout, infinity}, {ip_v6_disable, true}, {user_dir, UserDir}],
+ SMiscOpt0 = [{ip_v6_disable, false}, {user_dir, UserDir}, {system_dir, SystemDir}],
+ SMiscOpt1 = [{ip_v6_disable, true}, {user_dir, UserDir}, {system_dir, SystemDir}],
+
+ ClientOpts = ?config(client_opts, Config),
+ ServerOpts = ?config(server_opts, Config),
+
+ basic_test([{client_opts, CMiscOpt0 ++ ClientOpts}, {server_opts, SMiscOpt0 ++ ServerOpts}]),
+ basic_test([{client_opts, CMiscOpt1 ++ ClientOpts}, {server_opts, SMiscOpt1 ++ ServerOpts}]).
+%%--------------------------------------------------------------------
exec(doc) ->
["Test api function ssh_connection:exec"];
@@ -500,13 +522,14 @@ internal_error(Config) when is_list(Config) ->
SystemDir = filename:join(?config(priv_dir, Config), system),
UserDir = ?config(priv_dir, Config),
- {_Pid, Host, Port} = ssh_test_lib:daemon([{system_dir, SystemDir},
+ {Pid, Host, Port} = ssh_test_lib:daemon([{system_dir, SystemDir},
{user_dir, UserDir},
{failfun, fun ssh_test_lib:failfun/2}]),
{error,"Internal error"} =
ssh:connect(Host, Port, [{silently_accept_hosts, true},
{user_dir, UserDir},
- {user_interaction, false}]).
+ {user_interaction, false}]),
+ ssh:stop_daemon(Pid).
%%--------------------------------------------------------------------
close(doc) ->
@@ -539,3 +562,12 @@ close(Config) when is_list(Config) ->
%%--------------------------------------------------------------------
%% Internal functions
%%--------------------------------------------------------------------
+
+basic_test(Config) ->
+ ClientOpts = ?config(client_opts, Config),
+ ServerOpts = ?config(server_opts, Config),
+
+ {Pid, Host, Port} = ssh_test_lib:daemon(ServerOpts),
+ {ok, CM} = ssh:connect(Host, Port, ClientOpts),
+ ok = ssh:close(CM),
+ ssh:stop_daemon(Pid).
diff --git a/lib/ssl/doc/src/Makefile b/lib/ssl/doc/src/Makefile
index 5d808d6727..8736913c72 100644
--- a/lib/ssl/doc/src/Makefile
+++ b/lib/ssl/doc/src/Makefile
@@ -117,15 +117,15 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/ssl/doc/src/notes.xml b/lib/ssl/doc/src/notes.xml
index 1e1fe0d119..a4da939d3e 100644
--- a/lib/ssl/doc/src/notes.xml
+++ b/lib/ssl/doc/src/notes.xml
@@ -30,7 +30,53 @@
</header>
<p>This document describes the changes made to the SSL application.</p>
- <section><title>SSL 5.0</title>
+ <section><title>SSL 5.0.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Robustness and improvement to distribution over SSL</p>
+ <p>
+ Fix a bug where ssl_tls_dist_proxy would crash at caller
+ timeout. Fix a bug where a timeout from the SSL layer
+ would block the distribution indefinately. Run the proxy
+ exclusively on the loopback interface. (Thanks to Paul
+ Guyot)</p>
+ <p>
+ Own Id: OTP-9915</p>
+ </item>
+ <item>
+ <p>
+ Fix setup loop of SSL TLS dist proxy</p>
+ <p>
+ Fix potential leak of processes waiting indefinately for
+ data from closed sockets during socket setup phase.
+ (Thanks to Paul Guyot)</p>
+ <p>
+ Own Id: OTP-9916</p>
+ </item>
+ <item>
+ <p>
+ Correct spelling of registered (Thanks to Richard
+ Carlsson)</p>
+ <p>
+ Own Id: OTP-9925</p>
+ </item>
+ <item>
+ <p>
+ Added TLS PRF function to the SSL API for generation of
+ additional key material from a TLS session. (Thanks to
+ Andreas Schultz)</p>
+ <p>
+ Own Id: OTP-10024</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>SSL 5.0</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 e019654685..28bf82b406 100644
--- a/lib/ssl/doc/src/ssl.xml
+++ b/lib/ssl/doc/src/ssl.xml
@@ -193,13 +193,13 @@
</item>
<tag>{depth, integer()}</tag>
- <item>Specifies the maximum
- verification depth, i.e. how far in a chain of certificates the
- verification process can proceed before the verification is
- considered to fail. Peer certificate = 0, CA certificate = 1,
- higher level CA certificate = 2, etc. The value 2 thus means
- that a chain can at most contain peer cert, CA cert, next CA
- cert, and an additional CA cert. The default value is 1.
+ <item>
+ The depth is the maximum number of non-self-issued
+ intermediate certificates that may follow the peer certificate
+ in a valid certification path. So if depth is 0 the PEER must
+ be signed by the trusted ROOT-CA directly, if 1 the path can
+ be PEER, CA, ROOT-CA, if it is 2 PEER, CA, CA, ROOT-CA and so
+ on. The default value is 1.
</item>
<tag>{verify_fun, {Verifyfun :: fun(), InitialUserState :: term()}}</tag>
diff --git a/lib/ssl/examples/certs/Makefile b/lib/ssl/examples/certs/Makefile
index a4f067ade6..549f11d709 100644
--- a/lib/ssl/examples/certs/Makefile
+++ b/lib/ssl/examples/certs/Makefile
@@ -54,8 +54,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/certs
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/certs"
tar cf - etc | \
- (cd $(RELSYSDIR)/examples/certs; tar xf -)
- chmod -R ug+rw $(RELSYSDIR)/examples
+ (cd "$(RELSYSDIR)/examples/certs"; tar xf -)
+ chmod -R ug+rw "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/ssl/examples/src/Makefile b/lib/ssl/examples/src/Makefile
index c5f31b689c..420634c97e 100644
--- a/lib/ssl/examples/src/Makefile
+++ b/lib/ssl/examples/src/Makefile
@@ -63,10 +63,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples/src
- $(INSTALL_DIR) $(RELSYSDIR)/examples/ebin
- (cd ..; tar cf - src ebin | (cd $(RELSYSDIR)/examples; tar xf -))
- chmod -R ug+w $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples/ebin"
+ (cd ..; tar cf - src ebin | (cd "$(RELSYSDIR)/examples"; tar xf -))
+ chmod -R ug+w "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/ssl/src/Makefile b/lib/ssl/src/Makefile
index dc69b53b28..a08444b8dd 100644
--- a/lib/ssl/src/Makefile
+++ b/lib/ssl/src/Makefile
@@ -37,6 +37,9 @@ RELSYSDIR = $(RELEASE_PATH)/lib/ssl-$(VSN)
# Common Macros
# ----------------------------------------------------
+BEHAVIOUR_MODULES= \
+ ssl_session_cache_api
+
MODULES= \
ssl \
ssl_alert \
@@ -53,7 +56,6 @@ MODULES= \
ssl_handshake \
ssl_manager \
ssl_session \
- ssl_session_cache_api \
ssl_session_cache \
ssl_record \
ssl_ssl2 \
@@ -66,10 +68,15 @@ INTERNAL_HRL_FILES = \
ssl_alert.hrl ssl_cipher.hrl ssl_handshake.hrl ssl_internal.hrl \
ssl_record.hrl
-ERL_FILES= $(MODULES:%=%.erl)
+ERL_FILES= \
+ $(MODULES:%=%.erl) \
+ $(BEHAVIOUR_MODULES:%=%.erl)
+
TARGET_FILES= $(MODULES:%=$(EBIN)/%.$(EMULATOR))
+BEHAVIOUR_TARGET_FILES= $(BEHAVIOUR_MODULES:%=$(EBIN)/%.$(EMULATOR))
+
APP_FILE= ssl.app
APPUP_FILE= ssl.appup
@@ -83,6 +90,7 @@ APPUP_TARGET= $(EBIN)/$(APPUP_FILE)
# ----------------------------------------------------
EXTRA_ERLC_FLAGS = +warn_unused_vars
ERL_COMPILE_FLAGS += -I$(ERL_TOP)/lib/kernel/src \
+ -pz $(EBIN) \
-pz $(ERL_TOP)/lib/public_key/ebin \
$(EXTRA_ERLC_FLAGS) -DVSN=\"$(VSN)\"
@@ -91,6 +99,8 @@ ERL_COMPILE_FLAGS += -I$(ERL_TOP)/lib/kernel/src \
# Targets
# ----------------------------------------------------
+$(TARGET_FILES): $(BEHAVIOUR_TARGET_FILES)
+
debug opt: $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET)
clean:
@@ -105,23 +115,18 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
docs:
+
# ----------------------------------------------------
# Release Target
# ----------------------------------------------------
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) \
- $(APPUP_TARGET) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(BEHAVIOUR_TARGET_FILES) $(TARGET_FILES) $(APP_TARGET) \
+ $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
release_docs_spec:
-
-
-
-
-
-
diff --git a/lib/ssl/src/ssl.erl b/lib/ssl/src/ssl.erl
index 0bcdffbeff..5e3ced144a 100644
--- a/lib/ssl/src/ssl.erl
+++ b/lib/ssl/src/ssl.erl
@@ -30,7 +30,7 @@
controlling_process/2, listen/2, pid/1, peername/1, peercert/1,
recv/2, recv/3, send/2, getopts/2, setopts/2, sockname/1,
versions/0, session_info/1, format_error/1,
- renegotiate/1, prf/5]).
+ renegotiate/1, prf/5, clear_pem_cache/0]).
-deprecated({pid, 1, next_major_release}).
@@ -431,6 +431,15 @@ prf(#sslsocket{pid = Pid, fd = new_ssl},
Secret, Label, Seed, WantedLength) ->
ssl_connection:prf(Pid, Secret, Label, Seed, WantedLength).
+
+%%--------------------------------------------------------------------
+-spec clear_pem_cache() -> ok.
+%%
+%% Description: Clear the PEM cache
+%%--------------------------------------------------------------------
+clear_pem_cache() ->
+ ssl_manager:clear_pem_cache().
+
%%---------------------------------------------------------------
-spec format_error({error, term()}) -> list().
%%
@@ -532,7 +541,7 @@ handle_options(Opts0, _Role) ->
throw({error, {eoptions, {verify, Value}}})
end,
- CertFile = handle_option(certfile, Opts, ""),
+ CertFile = handle_option(certfile, Opts, <<>>),
SSLOptions = #ssl_options{
versions = handle_option(versions, Opts, []),
@@ -619,8 +628,12 @@ validate_option(depth, Value) when is_integer(Value),
validate_option(cert, Value) when Value == undefined;
is_binary(Value) ->
Value;
-validate_option(certfile, Value) when Value == undefined; is_list(Value) ->
+validate_option(certfile, undefined = Value) ->
Value;
+validate_option(certfile, Value) when is_binary(Value) ->
+ Value;
+validate_option(certfile, Value) when is_list(Value) ->
+ list_to_binary(Value);
validate_option(key, undefined) ->
undefined;
@@ -631,8 +644,13 @@ validate_option(key, {KeyType, Value}) when is_binary(Value),
KeyType == 'DSAPrivateKey';
KeyType == 'PrivateKeyInfo' ->
{KeyType, Value};
-validate_option(keyfile, Value) when is_list(Value) ->
+
+validate_option(keyfile, undefined) ->
+ <<>>;
+validate_option(keyfile, Value) when is_binary(Value) ->
Value;
+validate_option(keyfile, Value) when is_list(Value), Value =/= "" ->
+ list_to_binary(Value);
validate_option(password, Value) when is_list(Value) ->
Value;
@@ -642,16 +660,20 @@ validate_option(cacerts, Value) when Value == undefined;
%% certfile must be present in some cases otherwhise it can be set
%% to the empty string.
validate_option(cacertfile, undefined) ->
- "";
-validate_option(cacertfile, Value) when is_list(Value), Value =/= "" ->
+ <<>>;
+validate_option(cacertfile, Value) when is_binary(Value) ->
Value;
+validate_option(cacertfile, Value) when is_list(Value), Value =/= ""->
+ list_to_binary(Value);
validate_option(dh, Value) when Value == undefined;
is_binary(Value) ->
Value;
validate_option(dhfile, undefined = Value) ->
Value;
-validate_option(dhfile, Value) when is_list(Value), Value =/= "" ->
+validate_option(dhfile, Value) when is_binary(Value) ->
Value;
+validate_option(dhfile, Value) when is_list(Value), Value =/= "" ->
+ list_to_binary(Value);
validate_option(ciphers, Value) when is_list(Value) ->
Version = ssl_record:highest_protocol_version([]),
try cipher_suites(Version, Value)
diff --git a/lib/ssl/src/ssl_certificate_db.erl b/lib/ssl/src/ssl_certificate_db.erl
index cb2473576a..01ddf056c9 100644
--- a/lib/ssl/src/ssl_certificate_db.erl
+++ b/lib/ssl/src/ssl_certificate_db.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2007-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2007-2012. 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
@@ -24,12 +24,13 @@
-module(ssl_certificate_db).
-include("ssl_internal.hrl").
-include_lib("public_key/include/public_key.hrl").
+-include_lib("kernel/include/file.hrl").
-export([create/0, remove/1, add_trusted_certs/3,
- remove_trusted_certs/2, lookup_trusted_cert/4, foldl/3,
- lookup_cached_certs/2, cache_pem_file/4, uncache_pem_file/2, lookup/2]).
-
--type time() :: {non_neg_integer(), non_neg_integer(), non_neg_integer()}.
+ remove_trusted_certs/2, insert/3, remove/2, clear/1, db_size/1,
+ ref_count/3, lookup_trusted_cert/4, foldl/3,
+ lookup_cached_pem/2, cache_pem_file/2, cache_pem_file/3,
+ lookup/2]).
%%====================================================================
%% Internal application API
@@ -43,9 +44,14 @@
%% the process that called create may call the other functions.
%%--------------------------------------------------------------------
create() ->
- [ets:new(ssl_otp_certificate_db, [set, protected]),
- ets:new(ssl_file_to_ref, [set, protected]),
- ets:new(ssl_pid_to_file, [bag, private])].
+ [%% Let connection process delete trusted certs
+ %% that can only belong to one connection. (Supplied directly
+ %% on DER format to ssl:connect/listen.)
+ ets:new(ssl_otp_cacertificate_db, [set, public]),
+ %% Let connection processes call ref_count/3 directly
+ ets:new(ssl_otp_ca_file_ref, [set, public]),
+ ets:new(ssl_otp_pem_cache, [set, protected])
+ ].
%%--------------------------------------------------------------------
-spec remove([db_handle()]) -> term().
@@ -53,7 +59,9 @@ create() ->
%% Description: Removes database db
%%--------------------------------------------------------------------
remove(Dbs) ->
- lists:foreach(fun(Db) -> true = ets:delete(Db) end, Dbs).
+ lists:foreach(fun(Db) ->
+ true = ets:delete(Db)
+ end, Dbs).
%%--------------------------------------------------------------------
-spec lookup_trusted_cert(db_handle(), certdb_ref(), serialnumber(), issuer()) ->
@@ -72,11 +80,14 @@ lookup_trusted_cert(DbHandle, Ref, SerialNumber, Issuer) ->
{ok, Certs}
end.
-lookup_cached_certs(DbHandle, File) ->
- ets:lookup(DbHandle, {file, File}).
+lookup_cached_pem([_, _, PemChache], MD5) ->
+ lookup_cached_pem(PemChache, MD5);
+lookup_cached_pem(PemChache, MD5) ->
+ lookup(MD5, PemChache).
%%--------------------------------------------------------------------
--spec add_trusted_certs(pid(), string() | {der, list()}, [db_handle()]) -> {ok, [db_handle()]}.
+-spec add_trusted_certs(pid(), {erlang:timestamp(), string()} |
+ {der, list()}, [db_handle()]) -> {ok, [db_handle()]}.
%%
%% Description: Adds the trusted certificates from file <File> to the
%% runtime database. Returns Ref that should be handed to lookup_trusted_cert
@@ -86,82 +97,55 @@ add_trusted_certs(_Pid, {der, DerList}, [CerDb, _,_]) ->
NewRef = make_ref(),
add_certs_from_der(DerList, NewRef, CerDb),
{ok, NewRef};
-add_trusted_certs(Pid, File, [CertsDb, FileToRefDb, PidToFileDb]) ->
- Ref = case lookup(File, FileToRefDb) of
- undefined ->
- NewRef = make_ref(),
- add_certs_from_file(File, NewRef, CertsDb),
- insert(File, NewRef, 1, FileToRefDb),
- NewRef;
- [OldRef] ->
- ref_count(File,FileToRefDb,1),
- OldRef
- end,
- insert(Pid, File, PidToFileDb),
- {ok, Ref}.
+
+add_trusted_certs(_Pid, File, [CertsDb, RefDb, PemChache] = Db) ->
+ MD5 = crypto:md5(File),
+ case lookup_cached_pem(Db, MD5) of
+ [{_Content, Ref}] ->
+ ref_count(Ref, RefDb, 1),
+ {ok, Ref};
+ [Content] ->
+ Ref = make_ref(),
+ insert(Ref, [], 1, RefDb),
+ insert(MD5, {Content, Ref}, PemChache),
+ add_certs_from_pem(Content, Ref, CertsDb),
+ {ok, Ref};
+ undefined ->
+ new_trusted_cert_entry({MD5, File}, Db)
+ end.
%%--------------------------------------------------------------------
--spec cache_pem_file(pid(), string(), time(), [db_handle()]) -> term().
+-spec cache_pem_file(string(), [db_handle()]) -> term().
+-spec cache_pem_file(reference(), string(), [db_handle()]) -> term().
%%
%% Description: Cache file as binary in DB
%%--------------------------------------------------------------------
-cache_pem_file(Pid, File, Time, [CertsDb, _FileToRefDb, PidToFileDb]) ->
- {ok, PemBin} = file:read_file(File),
+cache_pem_file({MD5, File}, [_CertsDb, _RefDb, PemChache]) ->
+ {ok, PemBin} = file:read_file(File),
Content = public_key:pem_decode(PemBin),
- insert({file, File}, {Time, Content}, CertsDb),
- insert(Pid, File, PidToFileDb),
+ insert(MD5, Content, PemChache),
{ok, Content}.
-%--------------------------------------------------------------------
--spec uncache_pem_file(string(), [db_handle()]) -> no_return().
-%%
-%% Description: If a cached file is no longer valid (changed on disk)
-%% we must terminate the connections using the old file content, and
-%% when those processes are finish the cache will be cleaned. It is
-%% a rare but possible case a new ssl client/server is started with
-%% a filename with the same name as previously started client/server
-%% but with different content.
-%% --------------------------------------------------------------------
-uncache_pem_file(File, [_CertsDb, _FileToRefDb, PidToFileDb]) ->
- Pids = select(PidToFileDb, [{{'$1', File},[],['$$']}]),
- lists:foreach(fun([Pid]) ->
- exit(Pid, shutdown)
- end, Pids).
-
-%%--------------------------------------------------------------------
--spec remove_trusted_certs(pid(), [db_handle()]) -> term().
-
-%%
-%% Description: Removes trusted certs originating from
-%% the file associated to Pid from the runtime database.
-%%--------------------------------------------------------------------
-remove_trusted_certs(Pid, [CertsDb, FileToRefDb, PidToFileDb]) ->
- Files = lookup(Pid, PidToFileDb),
- delete(Pid, PidToFileDb),
- Clear = fun(File) ->
- delete({file,File}, CertsDb),
- try
- 0 = ref_count(File, FileToRefDb, -1),
- case lookup(File, FileToRefDb) of
- [Ref] when is_reference(Ref) ->
- remove_certs(Ref, CertsDb);
- _ -> ok
- end,
- delete(File, FileToRefDb)
- catch _:_ ->
- ok
- end
- end,
- case Files of
- undefined -> ok;
- _ ->
- [Clear(File) || File <- Files],
- ok
- end.
+cache_pem_file(Ref, {MD5, File}, [_CertsDb, _RefDb, PemChache]) ->
+ {ok, PemBin} = file:read_file(File),
+ Content = public_key:pem_decode(PemBin),
+ insert(MD5, {Content, Ref}, PemChache),
+ {ok, Content}.
+
+remove_trusted_certs(Ref, CertsDb) ->
+ remove_certs(Ref, CertsDb).
+
+%%--------------------------------------------------------------------
+-spec remove(term(), db_handle()) -> term().
+%%
+%% Description: Removes an element in a <Db>.
+%%--------------------------------------------------------------------
+remove(Key, Db) ->
+ _ = ets:delete(Db, Key).
%%--------------------------------------------------------------------
-spec lookup(term(), db_handle()) -> term() | undefined.
%%
-%% Description: Looks up an element in a certificat <Db>.
+%% Description: Looks up an element in a <Db>.
%%--------------------------------------------------------------------
lookup(Key, Db) ->
case ets:lookup(Db, Key) of
@@ -184,25 +168,47 @@ lookup(Key, Db) ->
%%--------------------------------------------------------------------
foldl(Fun, Acc0, Cache) ->
ets:foldl(Fun, Acc0, Cache).
-
+
%%--------------------------------------------------------------------
-%%% Internal functions
+-spec ref_count(term(), db_handle(), integer()) -> integer().
+%%
+%% Description: Updates a reference counter in a <Db>.
+%%--------------------------------------------------------------------
+ref_count(Key, Db, N) ->
+ ets:update_counter(Db,Key,N).
+
+%%--------------------------------------------------------------------
+-spec clear(db_handle()) -> term().
+%%
+%% Description: Clears the cache
+%%--------------------------------------------------------------------
+clear(Db) ->
+ ets:delete_all_objects(Db).
+
+%%--------------------------------------------------------------------
+-spec db_size(db_handle()) -> integer().
+%%
+%% Description: Returns the size of the db
+%%--------------------------------------------------------------------
+db_size(Db) ->
+ ets:info(Db, size).
+
+%%--------------------------------------------------------------------
+%%-spec insert(Key::term(), Data::term(), Db::db_handle()) -> no_return().
+%%
+%% Description: Inserts data into <Db>
%%--------------------------------------------------------------------
insert(Key, Data, Db) ->
true = ets:insert(Db, {Key, Data}).
+%%--------------------------------------------------------------------
+%%% Internal functions
+%%--------------------------------------------------------------------
+insert(Key, [], Count, Db) ->
+ true = ets:insert(Db, {Key, Count});
insert(Key, Data, Count, Db) ->
true = ets:insert(Db, {Key, Count, Data}).
-ref_count(Key, Db,N) ->
- ets:update_counter(Db,Key,N).
-
-delete(Key, Db) ->
- _ = ets:delete(Db, Key).
-
-select(Db, MatchSpec)->
- ets:select(Db, MatchSpec).
-
remove_certs(Ref, CertsDb) ->
ets:match_delete(CertsDb, {{Ref, '_', '_'}, '_'}).
@@ -210,10 +216,8 @@ add_certs_from_der(DerList, Ref, CertsDb) ->
Add = fun(Cert) -> add_certs(Cert, Ref, CertsDb) end,
[Add(Cert) || Cert <- DerList].
-add_certs_from_file(File, Ref, CertsDb) ->
+add_certs_from_pem(PemEntries, Ref, CertsDb) ->
Add = fun(Cert) -> add_certs(Cert, Ref, CertsDb) end,
- {ok, PemBin} = file:read_file(File),
- PemEntries = public_key:pem_decode(PemBin),
[Add(Cert) || {'Certificate', Cert, not_encrypted} <- PemEntries].
add_certs(Cert, Ref, CertsDb) ->
@@ -229,3 +233,10 @@ add_certs(Cert, Ref, CertsDb) ->
"it could not be correctly decoded.~n", []),
error_logger:info_report(Report)
end.
+
+new_trusted_cert_entry(FileRef, [CertsDb, RefDb, _] = Db) ->
+ Ref = make_ref(),
+ insert(Ref, [], 1, RefDb),
+ {ok, Content} = cache_pem_file(Ref, FileRef, Db),
+ add_certs_from_pem(Content, Ref, CertsDb),
+ {ok, Ref}.
diff --git a/lib/ssl/src/ssl_connection.erl b/lib/ssl/src/ssl_connection.erl
index 6c06baff98..c57930e821 100644
--- a/lib/ssl/src/ssl_connection.erl
+++ b/lib/ssl/src/ssl_connection.erl
@@ -47,8 +47,8 @@
-export([start_link/7]).
%% gen_fsm callbacks
--export([init/1, hello/2, certify/2, cipher/2, connection/2,
- abbreviated/2, handle_event/3,
+-export([init/1, hello/2, certify/2, cipher/2,
+ abbreviated/2, connection/2, handle_event/3,
handle_sync_event/4, handle_info/3, terminate/3, code_change/4]).
-record(state, {
@@ -83,13 +83,13 @@
diffie_hellman_params, % PKIX: #'DHParameter'{} relevant for server side
diffie_hellman_keys, % {PublicKey, PrivateKey}
premaster_secret, %
- cert_db_ref, % ets_table()
- from, % term(), where to reply
+ file_ref_db, % ets()
+ cert_db_ref, % ref()
bytes_to_read, % integer(), # bytes to read in passive mode
user_data_buffer, % binary()
log_alert, % boolean()
renegotiation, % {boolean(), From | internal | peer}
- recv_from, %
+ start_or_recv_from, % "gen_fsm From"
send_queue, % queue()
terminated = false, %
allow_renegotiate = true
@@ -297,39 +297,30 @@ prf(ConnectionPid, Secret, Label, Seed, WantedLength) ->
%% does not return until Module:init/1 has returned.
%%--------------------------------------------------------------------
start_link(Role, Host, Port, Socket, Options, User, CbInfo) ->
- gen_fsm:start_link(?MODULE, [Role, Host, Port, Socket, Options,
- User, CbInfo], []).
+ {ok, proc_lib:spawn_link(?MODULE, init, [[Role, Host, Port, Socket, Options, User, CbInfo]])}.
-%%====================================================================
-%% gen_fsm callbacks
-%%====================================================================
-%%--------------------------------------------------------------------
-%% 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
-%% initialize.
-%%--------------------------------------------------------------------
-init([Role, Host, Port, Socket, {SSLOpts0, _} = Options,
- User, CbInfo]) ->
+init([Role, Host, Port, Socket, {SSLOpts0, _} = Options, User, CbInfo]) ->
State0 = initial_state(Role, Host, Port, Socket, Options, User, CbInfo),
Hashes0 = ssl_handshake:init_hashes(),
TimeStamp = calendar:datetime_to_gregorian_seconds({date(), time()}),
try ssl_init(SSLOpts0, Role) of
- {ok, Ref, CertDbHandle, CacheHandle, OwnCert, Key, DHParams} ->
+ {ok, Ref, CertDbHandle, FileRefHandle, CacheHandle, OwnCert, Key, DHParams} ->
Session = State0#state.session,
State = State0#state{tls_handshake_hashes = Hashes0,
session = Session#session{own_certificate = OwnCert,
time_stamp = TimeStamp},
+ file_ref_db = FileRefHandle,
cert_db_ref = Ref,
cert_db = CertDbHandle,
session_cache = CacheHandle,
private_key = Key,
diffie_hellman_params = DHParams},
- {ok, hello, State, get_timeout(State)}
- catch
+ gen_fsm:enter_loop(?MODULE, [], hello, State, get_timeout(State))
+ catch
throw:Error ->
- {stop, Error}
+ gen_fsm:enter_loop(?MODULE, [], error, {Error,State0}, get_timeout(State0))
end.
-
+
%%--------------------------------------------------------------------
%% Description:There should be one instance of this function for each
%% possible state name. Whenever a gen_fsm receives an event sent
@@ -337,6 +328,7 @@ init([Role, Host, Port, Socket, {SSLOpts0, _} = Options,
%% same name as the current state name StateName is called to handle
%% the event. It is also called if a timeout occurs.
%%
+
%%--------------------------------------------------------------------
-spec hello(start | #hello_request{} | #client_hello{} | #server_hello{} | term(),
#state{}) -> gen_fsm_state_return().
@@ -344,23 +336,23 @@ init([Role, Host, Port, Socket, {SSLOpts0, _} = Options,
hello(start, #state{host = Host, port = Port, role = client,
ssl_options = SslOpts,
session = #session{own_certificate = Cert} = Session0,
+ session_cache = Cache, session_cache_cb = CacheCb,
transport_cb = Transport, socket = Socket,
- connection_states = ConnectionStates,
+ connection_states = ConnectionStates0,
renegotiation = {Renegotiation, _}} = State0) ->
- Hello = ssl_handshake:client_hello(Host, Port,
- ConnectionStates,
- SslOpts, Renegotiation, Cert),
+ Hello = ssl_handshake:client_hello(Host, Port, ConnectionStates0, SslOpts,
+ Cache, CacheCb, Renegotiation, Cert),
Version = Hello#client_hello.client_version,
Hashes0 = ssl_handshake:init_hashes(),
- {BinMsg, CS2, Hashes1} =
- encode_handshake(Hello, Version, ConnectionStates, Hashes0),
+ {BinMsg, ConnectionStates, Hashes} =
+ encode_handshake(Hello, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
- State1 = State0#state{connection_states = CS2,
- negotiated_version = Version, %% Requested version
+ State1 = State0#state{connection_states = ConnectionStates,
+ negotiated_version = Version, %% Requested version at this point
session =
Session0#session{session_id = Hello#client_hello.session_id},
- tls_handshake_hashes = Hashes1},
+ tls_handshake_hashes = Hashes},
{Record, State} = next_record(State1),
next_state(hello, hello, Record, State);
@@ -394,7 +386,8 @@ hello(#server_hello{cipher_suite = CipherSuite,
case ssl_session:is_new(OldId, NewId) of
true ->
- handle_new_session(NewId, CipherSuite, Compression, State);
+ handle_new_session(NewId, CipherSuite, Compression,
+ State#state{connection_states = ConnectionStates});
false ->
handle_resumed_session(NewId, State#state{connection_states = ConnectionStates})
end;
@@ -552,8 +545,8 @@ certify(#server_hello_done{},
role = client} = State0) ->
case ssl_handshake:master_secret(Version, Session,
ConnectionStates0, client) of
- {MasterSecret, ConnectionStates1} ->
- State = State0#state{connection_states = ConnectionStates1},
+ {MasterSecret, ConnectionStates} ->
+ State = State0#state{connection_states = ConnectionStates},
client_certify_and_key_exchange(State);
#alert{} = Alert ->
handle_own_alert(Alert, Version, certify, State0),
@@ -569,10 +562,10 @@ certify(#server_hello_done{},
role = client} = State0) ->
case ssl_handshake:master_secret(Version, PremasterSecret,
ConnectionStates0, client) of
- {MasterSecret, ConnectionStates1} ->
+ {MasterSecret, ConnectionStates} ->
Session = Session0#session{master_secret = MasterSecret},
- State = State0#state{connection_states = ConnectionStates1,
- session = Session},
+ State = State0#state{connection_states = ConnectionStates,
+ session = Session},
client_certify_and_key_exchange(State);
#alert{} = Alert ->
handle_own_alert(Alert, Version, certify, State0),
@@ -691,22 +684,24 @@ cipher(Msg, State) ->
%%--------------------------------------------------------------------
connection(#hello_request{}, #state{host = Host, port = Port,
socket = Socket,
- session = #session{own_certificate = Cert},
+ session = #session{own_certificate = Cert} = Session0,
+ session_cache = Cache, session_cache_cb = CacheCb,
ssl_options = SslOpts,
negotiated_version = Version,
transport_cb = Transport,
connection_states = ConnectionStates0,
renegotiation = {Renegotiation, _},
tls_handshake_hashes = Hashes0} = State0) ->
- Hello = ssl_handshake:client_hello(Host, Port, ConnectionStates0,
- SslOpts, Renegotiation, Cert),
+ Hello = ssl_handshake:client_hello(Host, Port, ConnectionStates0, SslOpts,
+ Cache, CacheCb, Renegotiation, Cert),
- {BinMsg, ConnectionStates1, Hashes1} =
+ {BinMsg, ConnectionStates, Hashes} =
encode_handshake(Hello, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
{Record, State} = next_record(State0#state{connection_states =
- ConnectionStates1,
- tls_handshake_hashes = Hashes1}),
+ ConnectionStates,
+ session = Session0#session{session_id = Hello#client_hello.session_id},
+ tls_handshake_hashes = Hashes}),
next_state(connection, hello, Record, State);
connection(#client_hello{} = Hello, #state{role = server, allow_renegotiate = true} = State) ->
%% Mitigate Computational DoS attack
@@ -732,6 +727,7 @@ connection(timeout, State) ->
connection(Msg, State) ->
handle_unexpected_message(Msg, connection, State).
+
%%--------------------------------------------------------------------
%% Description: Whenever a gen_fsm receives an event sent using
%% gen_fsm:send_all_state_event/2, this function is called to handle
@@ -761,8 +757,8 @@ handle_sync_event({application_data, Data}, From, 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});
+handle_sync_event(start, StartFrom, hello, State) ->
+ hello(start, State#state{start_or_recv_from = StartFrom});
%% The two clauses below could happen if a server upgrades a socket in
%% active mode. Note that in this case we are lucky that
@@ -774,8 +770,10 @@ handle_sync_event(start, From, hello, State) ->
%% they upgrade a active socket.
handle_sync_event(start, _, connection, State) ->
{reply, connected, connection, State, get_timeout(State)};
-handle_sync_event(start, From, StateName, State) ->
- {next_state, StateName, State#state{from = From}, get_timeout(State)};
+handle_sync_event(start, _From, error, {Error, State = #state{}}) ->
+ {stop, {shutdown, Error}, {error, Error}, State};
+handle_sync_event(start, StartFrom, StateName, State) ->
+ {next_state, StateName, State#state{start_or_recv_from = StartFrom}, get_timeout(State)};
handle_sync_event(close, _, StateName, State) ->
%% Run terminate before returning
@@ -806,13 +804,13 @@ handle_sync_event({shutdown, How0}, _, StateName,
{stop, normal, Error, State}
end;
-handle_sync_event({recv, N}, From, connection = StateName, State0) ->
- passive_receive(State0#state{bytes_to_read = N, recv_from = From}, StateName);
+handle_sync_event({recv, N}, RecvFrom, connection = StateName, State0) ->
+ passive_receive(State0#state{bytes_to_read = N, start_or_recv_from = RecvFrom}, StateName);
%% Doing renegotiate wait with handling request until renegotiate is
%% finished. Will be handled by next_state_is_connection/2.
-handle_sync_event({recv, N}, From, StateName, State) ->
- {next_state, StateName, State#state{bytes_to_read = N, recv_from = From},
+handle_sync_event({recv, N}, RecvFrom, StateName, State) ->
+ {next_state, StateName, State#state{bytes_to_read = N, start_or_recv_from = RecvFrom},
get_timeout(State)};
handle_sync_event({new_user, User}, _From, StateName,
@@ -963,9 +961,9 @@ handle_info({CloseTag, Socket}, StateName,
{stop, normal, State};
handle_info({ErrorTag, Socket, econnaborted}, StateName,
- #state{socket = Socket, from = User, role = Role,
+ #state{socket = Socket, start_or_recv_from = StartFrom, role = Role,
error_tag = ErrorTag} = State) when StateName =/= connection ->
- alert_user(User, ?ALERT_REC(?FATAL, ?HANDSHAKE_FAILURE), Role),
+ alert_user(StartFrom, ?ALERT_REC(?FATAL, ?HANDSHAKE_FAILURE), Role),
{stop, normal, State};
handle_info({ErrorTag, Socket, Reason}, StateName, #state{socket = Socket,
@@ -1002,16 +1000,19 @@ terminate(Reason, connection, #state{negotiated_version = Version,
connection_states = ConnectionStates,
transport_cb = Transport,
socket = Socket, send_queue = SendQueue,
- renegotiation = Renegotiate}) ->
+ renegotiation = Renegotiate} = State) ->
+ handle_trusted_certs_db(State),
notify_senders(SendQueue),
notify_renegotiater(Renegotiate),
BinAlert = terminate_alert(Reason, Version, ConnectionStates),
Transport:send(Socket, BinAlert),
workaround_transport_delivery_problems(Socket, Transport, Reason),
Transport:close(Socket);
+
terminate(Reason, _StateName, #state{transport_cb = Transport,
socket = Socket, send_queue = SendQueue,
- renegotiation = Renegotiate}) ->
+ renegotiation = Renegotiate} = State) ->
+ handle_trusted_certs_db(State),
notify_senders(SendQueue),
notify_renegotiater(Renegotiate),
workaround_transport_delivery_problems(Socket, Transport, Reason),
@@ -1059,12 +1060,12 @@ ssl_init(SslOpts, Role) ->
init_manager_name(SslOpts#ssl_options.erl_dist),
- {ok, CertDbRef, CertDbHandle, CacheHandle, OwnCert} = init_certificates(SslOpts, Role),
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, OwnCert} = init_certificates(SslOpts, Role),
PrivateKey =
- init_private_key(CertDbHandle, SslOpts#ssl_options.key, SslOpts#ssl_options.keyfile,
+ init_private_key(PemCacheHandle, SslOpts#ssl_options.key, SslOpts#ssl_options.keyfile,
SslOpts#ssl_options.password, Role),
- DHParams = init_diffie_hellman(CertDbHandle, SslOpts#ssl_options.dh, SslOpts#ssl_options.dhfile, Role),
- {ok, CertDbRef, CertDbHandle, CacheHandle, OwnCert, PrivateKey, DHParams}.
+ DHParams = init_diffie_hellman(PemCacheHandle, SslOpts#ssl_options.dh, SslOpts#ssl_options.dhfile, Role),
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, CacheHandle, OwnCert, PrivateKey, DHParams}.
init_manager_name(false) ->
put(ssl_manager, ssl_manager);
@@ -1075,7 +1076,7 @@ init_certificates(#ssl_options{cacerts = CaCerts,
cacertfile = CACertFile,
certfile = CertFile,
cert = Cert}, Role) ->
- {ok, CertDbRef, CertDbHandle, CacheHandle} =
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle} =
try
Certs = case CaCerts of
undefined ->
@@ -1083,38 +1084,38 @@ init_certificates(#ssl_options{cacerts = CaCerts,
_ ->
{der, CaCerts}
end,
- {ok, _, _, _} = ssl_manager:connection_init(Certs, Role)
+ {ok, _, _, _, _, _} = ssl_manager:connection_init(Certs, Role)
catch
Error:Reason ->
handle_file_error(?LINE, Error, Reason, CACertFile, ecacertfile,
erlang:get_stacktrace())
end,
- init_certificates(Cert, CertDbRef, CertDbHandle, CacheHandle, CertFile, Role).
+ init_certificates(Cert, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, CertFile, Role).
-init_certificates(undefined, CertDbRef, CertDbHandle, CacheHandle, "", _) ->
- {ok, CertDbRef, CertDbHandle, CacheHandle, undefined};
+init_certificates(undefined, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, <<>>, _) ->
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, undefined};
-init_certificates(undefined, CertDbRef, CertDbHandle, CacheHandle, CertFile, client) ->
+init_certificates(undefined, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, CertFile, client) ->
try
- [OwnCert] = ssl_certificate:file_to_certificats(CertFile, CertDbHandle),
- {ok, CertDbRef, CertDbHandle, CacheHandle, OwnCert}
+ [OwnCert] = ssl_certificate:file_to_certificats(CertFile, PemCacheHandle),
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, OwnCert}
catch _Error:_Reason ->
- {ok, CertDbRef, CertDbHandle, CacheHandle, undefined}
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheHandle, undefined}
end;
-init_certificates(undefined, CertDbRef, CertDbHandle, CacheRef, CertFile, server) ->
+init_certificates(undefined, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheRef, CertFile, server) ->
try
- [OwnCert] = ssl_certificate:file_to_certificats(CertFile, CertDbHandle),
- {ok, CertDbRef, CertDbHandle, CacheRef, OwnCert}
+ [OwnCert] = ssl_certificate:file_to_certificats(CertFile, PemCacheHandle),
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheRef, OwnCert}
catch
Error:Reason ->
handle_file_error(?LINE, Error, Reason, CertFile, ecertfile,
erlang:get_stacktrace())
end;
-init_certificates(Cert, CertDbRef, CertDbHandle, CacheRef, _, _) ->
- {ok, CertDbRef, CertDbHandle, CacheRef, Cert}.
+init_certificates(Cert, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheRef, _, _) ->
+ {ok, CertDbRef, CertDbHandle, FileRefHandle, PemCacheHandle, CacheRef, Cert}.
-init_private_key(_, undefined, "", _Password, _Client) ->
+init_private_key(_, undefined, <<>>, _Password, _Client) ->
undefined;
init_private_key(DbHandle, undefined, KeyFile, Password, _) ->
try
@@ -1225,11 +1226,11 @@ certify_client(#state{client_certificate_requested = true, role = client,
socket = Socket,
tls_handshake_hashes = Hashes0} = State) ->
Certificate = ssl_handshake:certificate(OwnCert, CertDbHandle, CertDbRef, client),
- {BinCert, ConnectionStates1, Hashes1} =
+ {BinCert, ConnectionStates, Hashes} =
encode_handshake(Certificate, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinCert),
- State#state{connection_states = ConnectionStates1,
- tls_handshake_hashes = Hashes1};
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes};
certify_client(#state{client_certificate_requested = false} = State) ->
State.
@@ -1246,12 +1247,12 @@ verify_client_cert(#state{client_certificate_requested = true, role = client,
case ssl_handshake:client_certificate_verify(OwnCert, MasterSecret,
Version, PrivateKey, Hashes0) of
#certificate_verify{} = Verified ->
- {BinVerified, ConnectionStates1, Hashes1} =
+ {BinVerified, ConnectionStates, Hashes} =
encode_handshake(Verified, Version,
ConnectionStates0, Hashes0),
Transport:send(Socket, BinVerified),
- State#state{connection_states = ConnectionStates1,
- tls_handshake_hashes = Hashes1};
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes};
ignore ->
State;
#alert{} = Alert ->
@@ -1261,7 +1262,7 @@ verify_client_cert(#state{client_certificate_requested = false} = State) ->
State.
do_server_hello(Type, #state{negotiated_version = Version,
- session = #session{session_id = SessId} = Session,
+ session = #session{session_id = SessId},
connection_states = ConnectionStates0,
renegotiation = {Renegotiation, _}}
= State0) when is_atom(Type) ->
@@ -1269,29 +1270,13 @@ do_server_hello(Type, #state{negotiated_version = Version,
ServerHello =
ssl_handshake:server_hello(SessId, Version,
ConnectionStates0, Renegotiation),
- State1 = server_hello(ServerHello, State0),
+ State = server_hello(ServerHello, State0),
case Type of
new ->
- new_server_hello(ServerHello, State1);
+ new_server_hello(ServerHello, State);
resumed ->
- ConnectionStates1 = State1#state.connection_states,
- case ssl_handshake:master_secret(Version, Session,
- ConnectionStates1, server) of
- {_, ConnectionStates2} ->
- State2 = State1#state{connection_states=ConnectionStates2,
- session = Session},
- {ConnectionStates, Hashes} =
- finalize_handshake(State2, abbreviated),
- State3 = State2#state{connection_states =
- ConnectionStates,
- tls_handshake_hashes = Hashes},
- {Record, State} = next_record(State3),
- next_state(hello, abbreviated, Record, State);
- #alert{} = Alert ->
- handle_own_alert(Alert, Version, hello, State1),
- {stop, normal, State1}
- end
+ resumed_server_hello(State)
end.
new_server_hello(#server_hello{cipher_suite = CipherSuite,
@@ -1314,6 +1299,27 @@ new_server_hello(#server_hello{cipher_suite = CipherSuite,
{stop, normal, State0}
end.
+resumed_server_hello(#state{session = Session,
+ connection_states = ConnectionStates0,
+ negotiated_version = Version} = State0) ->
+
+ case ssl_handshake:master_secret(Version, Session,
+ ConnectionStates0, server) of
+ {_, ConnectionStates1} ->
+ State1 = State0#state{connection_states = ConnectionStates1,
+ session = Session},
+ {ConnectionStates, Hashes} =
+ finalize_handshake(State1, abbreviated),
+ State2 = State1#state{connection_states =
+ ConnectionStates,
+ tls_handshake_hashes = Hashes},
+ {Record, State} = next_record(State2),
+ next_state(hello, abbreviated, Record, State);
+ #alert{} = Alert ->
+ handle_own_alert(Alert, Version, hello, State0),
+ {stop, normal, State0}
+ end.
+
handle_new_session(NewId, CipherSuite, Compression, #state{session = Session0} = State0) ->
Session = Session0#session{session_id = NewId,
cipher_suite = CipherSuite,
@@ -1329,10 +1335,10 @@ handle_resumed_session(SessId, #state{connection_states = ConnectionStates0,
Session = CacheCb:lookup(Cache, {{Host, Port}, SessId}),
case ssl_handshake:master_secret(Version, Session,
ConnectionStates0, client) of
- {_, ConnectionStates1} ->
+ {_, ConnectionStates} ->
{Record, State} =
next_record(State0#state{
- connection_states = ConnectionStates1,
+ connection_states = ConnectionStates,
session = Session}),
next_state(hello, abbreviated, Record, State);
#alert{} = Alert ->
@@ -1385,16 +1391,16 @@ server_hello(ServerHello, #state{transport_cb = Transport,
server_hello_done(#state{transport_cb = Transport,
socket = Socket,
negotiated_version = Version,
- connection_states = ConnectionStates,
- tls_handshake_hashes = Hashes} = State) ->
+ connection_states = ConnectionStates0,
+ tls_handshake_hashes = Hashes0} = State) ->
HelloDone = ssl_handshake:server_hello_done(),
- {BinHelloDone, NewConnectionStates, NewHashes} =
- encode_handshake(HelloDone, Version, ConnectionStates, Hashes),
+ {BinHelloDone, ConnectionStates, Hashes} =
+ encode_handshake(HelloDone, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinHelloDone),
- State#state{connection_states = NewConnectionStates,
- tls_handshake_hashes = NewHashes}.
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes}.
certify_server(#state{key_algorithm = dh_anon} = State) ->
State;
@@ -1402,18 +1408,18 @@ certify_server(#state{key_algorithm = dh_anon} = State) ->
certify_server(#state{transport_cb = Transport,
socket = Socket,
negotiated_version = Version,
- connection_states = ConnectionStates,
- tls_handshake_hashes = Hashes,
+ connection_states = ConnectionStates0,
+ tls_handshake_hashes = Hashes0,
cert_db = CertDbHandle,
cert_db_ref = CertDbRef,
session = #session{own_certificate = OwnCert}} = State) ->
case ssl_handshake:certificate(OwnCert, CertDbHandle, CertDbRef, server) of
CertMsg = #certificate{} ->
- {BinCertMsg, NewConnectionStates, NewHashes} =
- encode_handshake(CertMsg, Version, ConnectionStates, Hashes),
+ {BinCertMsg, ConnectionStates, Hashes} =
+ encode_handshake(CertMsg, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinCertMsg),
- State#state{connection_states = NewConnectionStates,
- tls_handshake_hashes = NewHashes
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes
};
Alert = #alert{} ->
throw(Alert)
@@ -1443,12 +1449,12 @@ key_exchange(#state{role = server, key_algorithm = Algo,
Algo, ClientRandom,
ServerRandom,
PrivateKey}),
- {BinMsg, ConnectionStates, Hashes1} =
+ {BinMsg, ConnectionStates, Hashes} =
encode_handshake(Msg, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
State#state{connection_states = ConnectionStates,
diffie_hellman_keys = Keys,
- tls_handshake_hashes = Hashes1};
+ tls_handshake_hashes = Hashes};
key_exchange(#state{role = client,
connection_states = ConnectionStates0,
@@ -1459,11 +1465,11 @@ key_exchange(#state{role = client,
socket = Socket, transport_cb = Transport,
tls_handshake_hashes = Hashes0} = State) ->
Msg = rsa_key_exchange(PremasterSecret, PublicKeyInfo),
- {BinMsg, ConnectionStates1, Hashes1} =
+ {BinMsg, ConnectionStates, Hashes} =
encode_handshake(Msg, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
- State#state{connection_states = ConnectionStates1,
- tls_handshake_hashes = Hashes1};
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes};
key_exchange(#state{role = client,
connection_states = ConnectionStates0,
key_algorithm = Algorithm,
@@ -1475,11 +1481,11 @@ key_exchange(#state{role = client,
Algorithm == dhe_rsa;
Algorithm == dh_anon ->
Msg = ssl_handshake:key_exchange(client, {dh, DhPubKey}),
- {BinMsg, ConnectionStates1, Hashes1} =
+ {BinMsg, ConnectionStates, Hashes} =
encode_handshake(Msg, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
- State#state{connection_states = ConnectionStates1,
- tls_handshake_hashes = Hashes1}.
+ State#state{connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes}.
rsa_key_exchange(PremasterSecret, PublicKeyInfo = {Algorithm, _, _})
when Algorithm == ?rsaEncryption;
@@ -1501,12 +1507,12 @@ request_client_cert(#state{ssl_options = #ssl_options{verify = verify_peer},
socket = Socket,
transport_cb = Transport} = State) ->
Msg = ssl_handshake:certificate_request(ConnectionStates0, CertDbHandle, CertDbRef),
- {BinMsg, ConnectionStates1, Hashes1} =
+ {BinMsg, ConnectionStates, Hashes} =
encode_handshake(Msg, Version, ConnectionStates0, Hashes0),
Transport:send(Socket, BinMsg),
State#state{client_certificate_requested = true,
- connection_states = ConnectionStates1,
- tls_handshake_hashes = Hashes1};
+ connection_states = ConnectionStates,
+ tls_handshake_hashes = Hashes};
request_client_cert(#state{ssl_options = #ssl_options{verify = verify_none}} =
State) ->
State.
@@ -1697,7 +1703,7 @@ passive_receive(State0 = #state{user_data_buffer = Buffer}, StateName) ->
read_application_data(Data, #state{user_application = {_Mon, Pid},
socket_options = SOpts,
bytes_to_read = BytesToRead,
- recv_from = From,
+ start_or_recv_from = RecvFrom,
user_data_buffer = Buffer0} = State0) ->
Buffer1 = if
Buffer0 =:= <<>> -> Data;
@@ -1706,9 +1712,9 @@ read_application_data(Data, #state{user_application = {_Mon, Pid},
end,
case get_data(SOpts, BytesToRead, Buffer1) of
{ok, ClientData, Buffer} -> % Send data
- SocketOpt = deliver_app_data(SOpts, ClientData, Pid, From),
+ SocketOpt = deliver_app_data(SOpts, ClientData, Pid, RecvFrom),
State = State0#state{user_data_buffer = Buffer,
- recv_from = undefined,
+ start_or_recv_from = undefined,
bytes_to_read = 0,
socket_options = SocketOpt
},
@@ -1723,7 +1729,7 @@ read_application_data(Data, #state{user_application = {_Mon, Pid},
{more, Buffer} -> % no reply, we need more data
next_record(State0#state{user_data_buffer = Buffer});
{error,_Reason} -> %% Invalid packet in packet mode
- deliver_packet_error(SOpts, Buffer1, Pid, From),
+ deliver_packet_error(SOpts, Buffer1, Pid, RecvFrom),
{stop, normal, State0}
end.
@@ -1843,8 +1849,9 @@ format_reply(binary, _, N, Data) when N > 0 -> % Header mode
format_reply(binary, _, _, Data) ->
Data;
format_reply(list, Packet, _, Data)
- when Packet == http; Packet == {http, headers}; Packet == http_bin; Packet == {http_bin, headers}; Packet == httph;
- Packet == httph_bin->
+ when Packet == http; Packet == {http, headers};
+ Packet == http_bin; Packet == {http_bin, headers};
+ Packet == httph; Packet == httph_bin ->
Data;
format_reply(list, _,_, Data) ->
binary_to_list(Data).
@@ -2008,9 +2015,9 @@ next_state_connection(StateName, #state{send_queue = Queue0,
%% premaster_secret and public_key_info (only needed during handshake)
%% to reduce memory foot print of a connection.
next_state_is_connection(_, State =
- #state{recv_from = From,
+ #state{start_or_recv_from = RecvFrom,
socket_options =
- #socket_options{active = false}}) when From =/= undefined ->
+ #socket_options{active = false}}) when RecvFrom =/= undefined ->
passive_receive(State#state{premaster_secret = undefined,
public_key_info = undefined,
tls_handshake_hashes = {<<>>, <<>>}}, connection);
@@ -2073,7 +2080,7 @@ initial_state(Role, Host, Port, Socket, {SSLOptions, SocketOptions}, User,
log_alert = true,
session_cache_cb = SessionCacheCb,
renegotiation = {false, first},
- recv_from = undefined,
+ start_or_recv_from = undefined,
send_queue = queue:new()
}.
@@ -2177,7 +2184,7 @@ handle_alerts([Alert | Alerts], {next_state, StateName, State, _Timeout}) ->
handle_alerts(Alerts, handle_alert(Alert, StateName, State)).
handle_alert(#alert{level = ?FATAL} = Alert, StateName,
- #state{from = From, host = Host, port = Port, session = Session,
+ #state{start_or_recv_from = From, host = Host, port = Port, session = Session,
user_application = {_Mon, Pid},
log_alert = Log, role = Role, socket_options = Opts} = State) ->
invalidate_session(Role, Host, Port, Session),
@@ -2259,13 +2266,13 @@ handle_own_alert(Alert, Version, StateName,
ok
end.
-handle_normal_shutdown(Alert, _, #state{from = User, role = Role, renegotiation = {false, first}}) ->
- alert_user(User, Alert, Role);
+handle_normal_shutdown(Alert, _, #state{start_or_recv_from = StartFrom, role = Role, renegotiation = {false, first}}) ->
+ alert_user(StartFrom, Alert, Role);
handle_normal_shutdown(Alert, StateName, #state{socket_options = Opts,
user_application = {_Mon, Pid},
- from = User, role = Role}) ->
- alert_user(StateName, Opts, Pid, User, Alert, Role).
+ start_or_recv_from = RecvFrom, role = Role}) ->
+ alert_user(StateName, Opts, Pid, RecvFrom, Alert, Role).
handle_unexpected_message(Msg, Info, #state{negotiated_version = Version} = State) ->
Alert = ?ALERT_REC(?FATAL,?UNEXPECTED_MESSAGE),
@@ -2291,9 +2298,9 @@ ack_connection(#state{renegotiation = {true, From}} = State) ->
gen_fsm:reply(From, ok),
State#state{renegotiation = undefined};
ack_connection(#state{renegotiation = {false, first},
- from = From} = State) when From =/= undefined ->
- gen_fsm:reply(From, connected),
- State#state{renegotiation = undefined};
+ start_or_recv_from = StartFrom} = State) when StartFrom =/= undefined ->
+ gen_fsm:reply(StartFrom, connected),
+ State#state{renegotiation = undefined, start_or_recv_from = undefined};
ack_connection(State) ->
State.
@@ -2359,7 +2366,29 @@ linux_workaround_transport_delivery_problems(#alert{level = ?FATAL}, Socket) ->
linux_workaround_transport_delivery_problems(_, _) ->
ok.
-get_timeout(#state{ssl_options=#ssl_options{hibernate_after=undefined}}) ->
+get_timeout(#state{ssl_options=#ssl_options{hibernate_after = undefined}}) ->
infinity;
-get_timeout(#state{ssl_options=#ssl_options{hibernate_after=HibernateAfter}}) ->
+get_timeout(#state{ssl_options=#ssl_options{hibernate_after = HibernateAfter}}) ->
HibernateAfter.
+
+handle_trusted_certs_db(#state{ssl_options = #ssl_options{cacertfile = <<>>}}) ->
+ %% No trusted certs specified
+ ok;
+handle_trusted_certs_db(#state{cert_db_ref = Ref,
+ cert_db = CertDb,
+ ssl_options = #ssl_options{cacertfile = undefined}}) ->
+ %% Certs provided as DER directly can not be shared
+ %% with other connections and it is safe to delete them when the connection ends.
+ ssl_certificate_db:remove_trusted_certs(Ref, CertDb);
+handle_trusted_certs_db(#state{file_ref_db = undefined}) ->
+ %% Something went wrong early (typically cacertfile does not exist) so there is nothing to handle
+ ok;
+handle_trusted_certs_db(#state{cert_db_ref = Ref,
+ file_ref_db = RefDb,
+ ssl_options = #ssl_options{cacertfile = File}}) ->
+ case ssl_certificate_db:ref_count(Ref, RefDb, -1) of
+ 0 ->
+ ssl_manager:clean_cert_db(Ref, File);
+ _ ->
+ ok
+ end.
diff --git a/lib/ssl/src/ssl_handshake.erl b/lib/ssl/src/ssl_handshake.erl
index 2e0a3de182..06d45966c1 100644
--- a/lib/ssl/src/ssl_handshake.erl
+++ b/lib/ssl/src/ssl_handshake.erl
@@ -30,7 +30,7 @@
-include("ssl_internal.hrl").
-include_lib("public_key/include/public_key.hrl").
--export([master_secret/4, client_hello/6, server_hello/4, hello/4,
+-export([master_secret/4, client_hello/8, server_hello/4, hello/4,
hello_request/0, certify/7, certificate/4,
client_certificate_verify/5, certificate_verify/5,
certificate_request/3, key_exchange/2, server_key_exchange_hash/2,
@@ -51,14 +51,17 @@
%%====================================================================
%%--------------------------------------------------------------------
-spec client_hello(host(), inet:port_number(), #connection_states{},
- #ssl_options{}, boolean(), der_cert()) -> #client_hello{}.
+ #ssl_options{}, integer(), atom(), boolean(), der_cert()) ->
+ #client_hello{}.
%%
%% Description: Creates a client hello message.
%%--------------------------------------------------------------------
-client_hello(Host, Port, ConnectionStates, #ssl_options{versions = Versions,
- ciphers = UserSuites}
- = SslOpts, Renegotiation, OwnCert) ->
-
+client_hello(Host, Port, ConnectionStates,
+ #ssl_options{versions = Versions,
+ ciphers = UserSuites
+ } = SslOpts,
+ Cache, CacheCb, Renegotiation, OwnCert) ->
+
Fun = fun(Version) ->
ssl_record:protocol_version(Version)
end,
@@ -67,15 +70,15 @@ client_hello(Host, Port, ConnectionStates, #ssl_options{versions = Versions,
SecParams = Pending#connection_state.security_parameters,
Ciphers = available_suites(UserSuites, Version),
- Id = ssl_manager:client_session_id(Host, Port, SslOpts, OwnCert),
+ Id = ssl_session:client_id({Host, Port, SslOpts}, Cache, CacheCb, OwnCert),
- #client_hello{session_id = Id,
+ #client_hello{session_id = Id,
client_version = Version,
cipher_suites = cipher_suites(Ciphers, Renegotiation),
compression_methods = ssl_record:compressions(),
random = SecParams#security_parameters.client_random,
- renegotiation_info =
- renegotiation_info(client, ConnectionStates, Renegotiation)
+ renegotiation_info =
+ renegotiation_info(client, ConnectionStates, Renegotiation)
}.
%%--------------------------------------------------------------------
@@ -584,24 +587,23 @@ path_validation_alert({bad_cert, unknown_ca}) ->
path_validation_alert(_) ->
?ALERT_REC(?FATAL, ?HANDSHAKE_FAILURE).
-select_session(Hello, Port, Session, Version,
+select_session(Hello, Port, Session, Version,
#ssl_options{ciphers = UserSuites} = SslOpts, Cache, CacheCb, Cert) ->
SuggestedSessionId = Hello#client_hello.session_id,
- SessionId = ssl_manager:server_session_id(Port, SuggestedSessionId,
- SslOpts, Cert),
-
- Suites = available_suites(Cert, UserSuites, Version),
- case ssl_session:is_new(SuggestedSessionId, SessionId) of
- true ->
- CipherSuite =
- select_cipher_suite(Hello#client_hello.cipher_suites, Suites),
+ {SessionId, Resumed} = ssl_session:server_id(Port, SuggestedSessionId,
+ SslOpts, Cert,
+ Cache, CacheCb),
+ Suites = available_suites(Cert, UserSuites, Version),
+ case Resumed of
+ undefined ->
+ CipherSuite = select_cipher_suite(Hello#client_hello.cipher_suites, Suites),
Compressions = Hello#client_hello.compression_methods,
Compression = select_compression(Compressions),
{new, Session#session{session_id = SessionId,
cipher_suite = CipherSuite,
compression_method = Compression}};
- false ->
- {resumed, CacheCb:lookup(Cache, {Port, SessionId})}
+ _ ->
+ {resumed, Resumed}
end.
available_suites(UserSuites, Version) ->
diff --git a/lib/ssl/src/ssl_manager.erl b/lib/ssl/src/ssl_manager.erl
index 6389ff03f5..3e947af2c9 100644
--- a/lib/ssl/src/ssl_manager.erl
+++ b/lib/ssl/src/ssl_manager.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2007-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2007-2012. 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
@@ -30,9 +30,9 @@
-export([start_link/1, start_link_dist/1,
connection_init/2, cache_pem_file/2,
lookup_trusted_cert/4,
- client_session_id/4, server_session_id/4,
+ new_session_id/1, clean_cert_db/2,
register_session/2, register_session/3, invalidate_session/2,
- invalidate_session/3]).
+ invalidate_session/3, clear_pem_cache/0]).
% Spawn export
-export([init_session_validator/1]).
@@ -56,9 +56,12 @@
-define('24H_in_msec', 8640000).
-define('24H_in_sec', 8640).
+-define(GEN_UNIQUE_ID_MAX_TRIES, 10).
-define(SESSION_VALIDATION_INTERVAL, 60000).
--define(CERTIFICATE_CACHE_CLEANUP, 30000).
+-define(CLEAR_PEM_CACHE, 120000).
-define(CLEAN_SESSION_DB, 60000).
+-define(CLEAN_CERT_DB, 500).
+-define(NOT_TO_BIG, 10).
%%====================================================================
%% API
@@ -82,26 +85,46 @@ start_link_dist(Opts) ->
gen_server:start_link({local, ssl_manager_dist}, ?MODULE, [ssl_manager_dist, Opts], []).
%%--------------------------------------------------------------------
--spec connection_init(string()| {der, list()}, client | server) ->
+-spec connection_init(binary()| {der, list()}, client | server) ->
{ok, certdb_ref(), db_handle(), db_handle()}.
%%
%% Description: Do necessary initializations for a new connection.
%%--------------------------------------------------------------------
+connection_init({der, _} = Trustedcerts, Role) ->
+ call({connection_init, Trustedcerts, Role});
+
+connection_init(<<>> = Trustedcerts, Role) ->
+ call({connection_init, Trustedcerts, Role});
+
connection_init(Trustedcerts, Role) ->
call({connection_init, Trustedcerts, Role}).
+
%%--------------------------------------------------------------------
--spec cache_pem_file(string(), term()) -> {ok, term()} | {error, reason()}.
+-spec cache_pem_file(binary(), term()) -> {ok, term()} | {error, reason()}.
%%
%% Description: Cach a pem file and return its content.
%%--------------------------------------------------------------------
cache_pem_file(File, DbHandle) ->
- try file:read_file_info(File) of
- {ok, #file_info{mtime = LastWrite}} ->
- cache_pem_file(File, LastWrite, DbHandle)
- catch
- _:Reason ->
- {error, Reason}
+ MD5 = crypto:md5(File),
+ case ssl_certificate_db:lookup_cached_pem(DbHandle, MD5) of
+ [{Content,_}] ->
+ {ok, Content};
+ [Content] ->
+ {ok, Content};
+ undefined ->
+ call({cache_pem, {MD5, File}})
end.
+
+%%--------------------------------------------------------------------
+-spec clear_pem_cache() -> ok.
+%%
+%% Description: Clear the PEM cache
+%%--------------------------------------------------------------------
+clear_pem_cache() ->
+ %% Not supported for distribution at the moement, should it be?
+ put(ssl_manager, ssl_manager),
+ call(unconditionally_clear_pem_cache).
+
%%--------------------------------------------------------------------
-spec lookup_trusted_cert(term(), reference(), serialnumber(), issuer()) ->
undefined |
@@ -114,22 +137,15 @@ lookup_trusted_cert(DbHandle, Ref, SerialNumber, Issuer) ->
ssl_certificate_db:lookup_trusted_cert(DbHandle, Ref, SerialNumber, Issuer).
%%--------------------------------------------------------------------
--spec client_session_id(host(), inet:port_number(), #ssl_options{},
- der_cert() | undefined) -> session_id().
+-spec new_session_id(integer()) -> session_id().
%%
-%% Description: Select a session id for the client.
+%% Description: Creates a session id for the server.
%%--------------------------------------------------------------------
-client_session_id(Host, Port, SslOpts, OwnCert) ->
- call({client_session_id, Host, Port, SslOpts, OwnCert}).
+new_session_id(Port) ->
+ call({new_session_id, Port}).
-%%--------------------------------------------------------------------
--spec server_session_id(host(), inet:port_number(), #ssl_options{},
- der_cert()) -> session_id().
-%%
-%% Description: Select a session id for the server.
-%%--------------------------------------------------------------------
-server_session_id(Port, SuggestedSessionId, SslOpts, OwnCert) ->
- call({server_session_id, Port, SuggestedSessionId, SslOpts, OwnCert}).
+clean_cert_db(Ref, File) ->
+ erlang:send_after(?CLEAN_CERT_DB, self(), {clean_cert_db, Ref, File}).
%%--------------------------------------------------------------------
-spec register_session(inet:port_number(), #session{}) -> ok.
@@ -177,6 +193,7 @@ init([Name, Opts]) ->
SessionCache = CacheCb:init(proplists:get_value(session_cb_init_args, Opts, [])),
Timer = erlang:send_after(SessionLifeTime * 1000,
self(), validate_sessions),
+ erlang:send_after(?CLEAR_PEM_CACHE, self(), clear_pem_cache),
{ok, #state{certificate_db = CertDb,
session_cache = SessionCache,
session_cache_cb = CacheCb,
@@ -194,55 +211,44 @@ init([Name, Opts]) ->
%%
%% Description: Handling call messages
%%--------------------------------------------------------------------
-handle_call({{connection_init, "", _Role}, Pid}, _From,
- #state{certificate_db = [CertDb |_],
+handle_call({{connection_init, <<>>, _Role}, _Pid}, _From,
+ #state{certificate_db = [CertDb, FileRefDb, PemChace],
session_cache = Cache} = State) ->
- erlang:monitor(process, Pid),
- Result = {ok, make_ref(),CertDb, Cache},
+ Result = {ok, make_ref(),CertDb, FileRefDb, PemChace, Cache},
{reply, Result, State};
handle_call({{connection_init, Trustedcerts, _Role}, Pid}, _From,
- #state{certificate_db = [CertDb|_] =Db,
+ #state{certificate_db = [CertDb, FileRefDb, PemChace] = Db,
session_cache = Cache} = State) ->
- erlang:monitor(process, Pid),
Result =
try
{ok, Ref} = ssl_certificate_db:add_trusted_certs(Pid, Trustedcerts, Db),
- {ok, Ref, CertDb, Cache}
+ {ok, Ref, CertDb, FileRefDb, PemChace, Cache}
catch
_:Reason ->
{error, Reason}
end,
{reply, Result, State};
-handle_call({{client_session_id, Host, Port, SslOpts, OwnCert}, _}, _,
- #state{session_cache = Cache,
- session_cache_cb = CacheCb} = State) ->
- Id = ssl_session:id({Host, Port, SslOpts}, Cache, CacheCb, OwnCert),
- {reply, Id, State};
-
-handle_call({{server_session_id, Port, SuggestedSessionId, SslOpts, OwnCert}, _},
+handle_call({{new_session_id,Port}, _},
_, #state{session_cache_cb = CacheCb,
- session_cache = Cache,
- session_lifetime = LifeTime} = State) ->
- Id = ssl_session:id(Port, SuggestedSessionId, SslOpts,
- Cache, CacheCb, LifeTime, OwnCert),
+ session_cache = Cache} = State) ->
+ Id = new_id(Port, ?GEN_UNIQUE_ID_MAX_TRIES, Cache, CacheCb),
{reply, Id, State};
-handle_call({{cache_pem, File, LastWrite}, Pid}, _,
+
+handle_call({{cache_pem, File}, _Pid}, _,
#state{certificate_db = Db} = State) ->
- try ssl_certificate_db:cache_pem_file(Pid, File, LastWrite, Db) of
+ try ssl_certificate_db:cache_pem_file(File, Db) of
Result ->
{reply, Result, State}
catch
_:Reason ->
{reply, {error, Reason}, State}
end;
-handle_call({{recache_pem, File, LastWrite}, Pid}, From,
- #state{certificate_db = Db} = State) ->
- ssl_certificate_db:uncache_pem_file(File, Db),
- cast({recache_pem, File, LastWrite, Pid, From}),
- {noreply, State}.
+handle_call({unconditionally_clear_pem_cache, _},_, #state{certificate_db = [_,_,PemChace]} = State) ->
+ ssl_certificate_db:clear(PemChace),
+ {reply, ok, State}.
%%--------------------------------------------------------------------
-spec handle_cast(msg(), #state{}) -> {noreply, #state{}}.
@@ -278,22 +284,7 @@ handle_cast({invalidate_session, Host, Port,
handle_cast({invalidate_session, Port, #session{session_id = ID} = Session},
#state{session_cache = Cache,
session_cache_cb = CacheCb} = State) ->
- invalidate_session(Cache, CacheCb, {Port, ID}, Session, State);
-
-handle_cast({recache_pem, File, LastWrite, Pid, From},
- #state{certificate_db = [_, FileToRefDb, _]} = State0) ->
- case ssl_certificate_db:lookup(File, FileToRefDb) of
- undefined ->
- {reply, Msg, State} =
- handle_call({{cache_pem, File, LastWrite}, Pid}, From, State0),
- gen_server:reply(From, Msg),
- {noreply, State};
- _ -> %% Send message to self letting cleanup messages be handled
- %% first so that no reference to the old version of file
- %% exists when we cache the new one.
- cast({recache_pem, File, LastWrite, Pid, From}),
- {noreply, State0}
- end.
+ invalidate_session(Cache, CacheCb, {Port, ID}, Session, State).
%%--------------------------------------------------------------------
-spec handle_info(msg(), #state{}) -> {noreply, #state{}}.
@@ -318,23 +309,38 @@ handle_info({delayed_clean_session, Key}, #state{session_cache = Cache,
CacheCb:delete(Cache, Key),
{noreply, State};
-handle_info({'EXIT', _, _}, State) ->
- %% Session validator died!! Do we need to take any action?
- %% maybe error log
+handle_info(clear_pem_cache, #state{certificate_db = [_,_,PemChace]} = State) ->
+ case ssl_certificate_db:db_size(PemChace) of
+ N when N < ?NOT_TO_BIG ->
+ ok;
+ _ ->
+ ssl_certificate_db:clear(PemChace)
+ end,
+ erlang:send_after(?CLEAR_PEM_CACHE, self(), clear_pem_cache),
{noreply, State};
-handle_info({'DOWN', _Ref, _Type, _Pid, ecacertfile}, State) ->
- {noreply, State};
-handle_info({'DOWN', _Ref, _Type, Pid, shutdown}, State) ->
- handle_info({remove_trusted_certs, Pid}, State);
-handle_info({'DOWN', _Ref, _Type, Pid, _Reason}, State) ->
- erlang:send_after(?CERTIFICATE_CACHE_CLEANUP, self(),
- {remove_trusted_certs, Pid}),
+handle_info({clean_cert_db, Ref, File},
+ #state{certificate_db = [CertDb,RefDb, PemCache]} = State) ->
+ case ssl_certificate_db:ref_count(Ref, RefDb, 0) of
+ 0 ->
+ MD5 = crypto:md5(File),
+ case ssl_certificate_db:lookup_cached_pem(MD5, PemCache) of
+ [{Content, Ref}] ->
+ ssl_certificate_db:insert(MD5, Content, PemCache);
+ undefined ->
+ ok
+ end,
+ ssl_certificate_db:remove(Ref, RefDb),
+ ssl_certificate_db:remove_trusted_certs(Ref, CertDb);
+ _ ->
+ ok
+ end,
{noreply, State};
-handle_info({remove_trusted_certs, Pid},
- #state{certificate_db = Db} = State) ->
- ssl_certificate_db:remove_trusted_certs(Pid, Db),
+
+handle_info({'EXIT', _, _}, State) ->
+ %% Session validator died!! Do we need to take any action?
+ %% maybe error log
{noreply, State};
handle_info(_Info, State) ->
@@ -406,19 +412,6 @@ session_validation({{Port, _}, Session}, LifeTime) ->
validate_session(Port, Session, LifeTime),
LifeTime.
-cache_pem_file(File, LastWrite, DbHandle) ->
- case ssl_certificate_db:lookup_cached_certs(DbHandle,File) of
- [{_, {Mtime, Content}}] ->
- case LastWrite of
- Mtime ->
- {ok, Content};
- _ ->
- call({recache_pem, File, LastWrite})
- end;
- [] ->
- call({cache_pem, File, LastWrite})
- end.
-
delay_time() ->
case application:get_env(ssl, session_delay_cleanup_time) of
{ok, Time} when is_integer(Time) ->
@@ -448,3 +441,28 @@ last_delay_timer({{_,_},_}, TRef, {LastServer, _}) ->
{LastServer, TRef};
last_delay_timer({_,_}, TRef, {_, LastClient}) ->
{TRef, LastClient}.
+
+%% If we can not generate a not allready in use session ID in
+%% ?GEN_UNIQUE_ID_MAX_TRIES we make the new session uncacheable The
+%% value of ?GEN_UNIQUE_ID_MAX_TRIES is stolen from open SSL which
+%% states : "If we can not find a session id in
+%% ?GEN_UNIQUE_ID_MAX_TRIES either the RAND code is broken or someone
+%% is trying to open roughly very close to 2^128 (or 2^256) SSL
+%% sessions to our server"
+new_id(_, 0, _, _) ->
+ <<>>;
+new_id(Port, Tries, Cache, CacheCb) ->
+ Id = crypto:rand_bytes(?NUM_OF_SESSION_ID_BYTES),
+ case CacheCb:lookup(Cache, {Port, Id}) of
+ undefined ->
+ Now = calendar:datetime_to_gregorian_seconds({date(), time()}),
+ %% New sessions can not be set to resumable
+ %% until handshake is compleate and the
+ %% other session values are set.
+ CacheCb:update(Cache, {Port, Id}, #session{session_id = Id,
+ is_resumable = false,
+ time_stamp = Now}),
+ Id;
+ _ ->
+ new_id(Port, Tries - 1, Cache, CacheCb)
+ end.
diff --git a/lib/ssl/src/ssl_session.erl b/lib/ssl/src/ssl_session.erl
index df5d7e0146..2ad422fc03 100644
--- a/lib/ssl/src/ssl_session.erl
+++ b/lib/ssl/src/ssl_session.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2007-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2007-2012. 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
@@ -28,9 +28,9 @@
-include("ssl_internal.hrl").
%% Internal application API
--export([is_new/2, id/4, id/7, valid_session/2]).
+-export([is_new/2, client_id/4, server_id/6, valid_session/2]).
--define(GEN_UNIQUE_ID_MAX_TRIES, 10).
+-define('24H_in_sec', 8640).
-type seconds() :: integer().
@@ -48,13 +48,13 @@ is_new(_ClientSuggestion, _ServerDecision) ->
true.
%%--------------------------------------------------------------------
--spec id({host(), inet:port_number(), #ssl_options{}}, db_handle(), atom(),
+-spec client_id({host(), inet:port_number(), #ssl_options{}}, db_handle(), atom(),
undefined | binary()) -> binary().
%%
-%% Description: Should be called by the client side to get an id
+%% Description: Should be called by the client side to get an id
%% for the client hello message.
%%--------------------------------------------------------------------
-id(ClientInfo, Cache, CacheCb, OwnCert) ->
+client_id(ClientInfo, Cache, CacheCb, OwnCert) ->
case select_session(ClientInfo, Cache, CacheCb, OwnCert) of
no_session ->
<<>>;
@@ -62,27 +62,6 @@ id(ClientInfo, Cache, CacheCb, OwnCert) ->
SessionId
end.
-%%--------------------------------------------------------------------
--spec id(inet:port_number(), binary(), #ssl_options{}, db_handle(),
- atom(), seconds(), binary()) -> binary().
-%%
-%% Description: Should be called by the server side to get an id
-%% for the server hello message.
-%%--------------------------------------------------------------------
-id(Port, <<>>, _, Cache, CacheCb, _, _) ->
- new_id(Port, ?GEN_UNIQUE_ID_MAX_TRIES, Cache, CacheCb);
-
-id(Port, SuggestedSessionId, #ssl_options{reuse_sessions = ReuseEnabled,
- reuse_session = ReuseFun},
- Cache, CacheCb, SecondLifeTime, OwnCert) ->
- case is_resumable(SuggestedSessionId, Port, ReuseEnabled,
- ReuseFun, Cache, CacheCb, SecondLifeTime, OwnCert) of
- true ->
- SuggestedSessionId;
- false ->
- new_id(Port, ?GEN_UNIQUE_ID_MAX_TRIES, Cache, CacheCb)
- end.
-%%--------------------------------------------------------------------
-spec valid_session(#session{}, seconds()) -> boolean().
%%
%% Description: Check that the session has not expired
@@ -91,57 +70,51 @@ valid_session(#session{time_stamp = TimeStamp}, LifeTime) ->
Now = calendar:datetime_to_gregorian_seconds({date(), time()}),
Now - TimeStamp < LifeTime.
+server_id(Port, <<>>, _SslOpts, _Cert, _, _) ->
+ {ssl_manager:new_session_id(Port), undefined};
+server_id(Port, SuggestedId,
+ #ssl_options{reuse_sessions = ReuseEnabled,
+ reuse_session = ReuseFun},
+ Cert, Cache, CacheCb) ->
+ LifeTime = case application:get_env(ssl, session_lifetime) of
+ {ok, Time} when is_integer(Time) -> Time;
+ _ -> ?'24H_in_sec'
+ end,
+ case is_resumable(SuggestedId, Port, ReuseEnabled,ReuseFun,
+ Cache, CacheCb, LifeTime, Cert)
+ of
+ {true, Resumed} ->
+ {SuggestedId, Resumed};
+ {false, undefined} ->
+ {ssl_manager:new_session_id(Port), undefined}
+ end.
+
%%--------------------------------------------------------------------
%%% Internal functions
%%--------------------------------------------------------------------
+select_session({_, _, #ssl_options{reuse_sessions=false}}, _Cache, _CacheCb, _OwnCert) ->
+ no_session;
select_session({HostIP, Port, SslOpts}, Cache, CacheCb, OwnCert) ->
Sessions = CacheCb:select_session(Cache, {HostIP, Port}),
select_session(Sessions, SslOpts, OwnCert).
select_session([], _, _) ->
no_session;
-
-select_session(Sessions, #ssl_options{ciphers = Ciphers,
- reuse_sessions = ReuseSession}, OwnCert) ->
- IsResumable =
- fun(Session) ->
- ReuseSession andalso resumable(Session#session.is_resumable) andalso
- lists:member(Session#session.cipher_suite, Ciphers)
- andalso (OwnCert == Session#session.own_certificate)
+select_session(Sessions, #ssl_options{ciphers = Ciphers}, OwnCert) ->
+ IsNotResumable =
+ fun([_Id, Session]) ->
+ not (resumable(Session#session.is_resumable) andalso
+ lists:member(Session#session.cipher_suite, Ciphers)
+ andalso (OwnCert == Session#session.own_certificate))
end,
- case [Id || [Id, Session] <- Sessions, IsResumable(Session)] of
- [] ->
- no_session;
- List ->
- hd(List)
- end.
-
-%% If we can not generate a not allready in use session ID in
-%% ?GEN_UNIQUE_ID_MAX_TRIES we make the new session uncacheable The
-%% value of ?GEN_UNIQUE_ID_MAX_TRIES is stolen from open SSL which
-%% states : "If we can not find a session id in
-%% ?GEN_UNIQUE_ID_MAX_TRIES either the RAND code is broken or someone
-%% is trying to open roughly very close to 2^128 (or 2^256) SSL
-%% sessions to our server"
-new_id(_, 0, _, _) ->
- <<>>;
-new_id(Port, Tries, Cache, CacheCb) ->
- Id = crypto:rand_bytes(?NUM_OF_SESSION_ID_BYTES),
- case CacheCb:lookup(Cache, {Port, Id}) of
- undefined ->
- Now = calendar:datetime_to_gregorian_seconds({date(), time()}),
- %% New sessions can not be set to resumable
- %% until handshake is compleate and the
- %% other session values are set.
- CacheCb:update(Cache, {Port, Id}, #session{session_id = Id,
- is_resumable = false,
- time_stamp = Now}),
- Id;
- _ ->
- new_id(Port, Tries - 1, Cache, CacheCb)
+ case lists:dropwhile(IsNotResumable, Sessions) of
+ [] -> no_session;
+ [[Id, _]|_] -> Id
end.
-is_resumable(SuggestedSessionId, Port, ReuseEnabled, ReuseFun, Cache,
+is_resumable(_, _, false, _, _, _, _, _) ->
+ {false, undefined};
+is_resumable(SuggestedSessionId, Port, true, ReuseFun, Cache,
CacheCb, SecondLifeTime, OwnCert) ->
case CacheCb:lookup(Cache, {Port, SuggestedSessionId}) of
#session{cipher_suite = CipherSuite,
@@ -149,14 +122,17 @@ is_resumable(SuggestedSessionId, Port, ReuseEnabled, ReuseFun, Cache,
compression_method = Compression,
is_resumable = IsResumable,
peer_certificate = PeerCert} = Session ->
- ReuseEnabled
- andalso resumable(IsResumable)
+ case resumable(IsResumable)
andalso (OwnCert == SessionOwnCert)
- andalso valid_session(Session, SecondLifeTime)
- andalso ReuseFun(SuggestedSessionId, PeerCert,
- Compression, CipherSuite);
+ andalso valid_session(Session, SecondLifeTime)
+ andalso ReuseFun(SuggestedSessionId, PeerCert,
+ Compression, CipherSuite)
+ of
+ true -> {true, Session};
+ false -> {false, undefined}
+ end;
undefined ->
- false
+ {false, undefined}
end.
resumable(new) ->
diff --git a/lib/ssl/src/ssl_session_cache.erl b/lib/ssl/src/ssl_session_cache.erl
index f9bbf905e1..5c6ee3c54c 100644
--- a/lib/ssl/src/ssl_session_cache.erl
+++ b/lib/ssl/src/ssl_session_cache.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2008-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2008-2012. 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
@@ -32,7 +32,7 @@
%% Description: Return table reference. Called by ssl_manager process.
%%--------------------------------------------------------------------
init(_) ->
- ets:new(cache_name(), [set, protected]).
+ ets:new(cache_name(), [ordered_set, protected]).
%%--------------------------------------------------------------------
%% Description: Handles cache table at termination of ssl manager.
diff --git a/lib/ssl/test/Makefile b/lib/ssl/test/Makefile
index 6b1da63d08..a0f54c0359 100644
--- a/lib/ssl/test/Makefile
+++ b/lib/ssl/test/Makefile
@@ -120,11 +120,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
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 ssl.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(HRL_FILES_NEEDED_IN_TEST) $(COVER_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DATA) ssl.spec ssl.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/ssl/test/ssl_basic_SUITE.erl b/lib/ssl/test/ssl_basic_SUITE.erl
index 590ecf33ca..5a52917d6c 100644
--- a/lib/ssl/test/ssl_basic_SUITE.erl
+++ b/lib/ssl/test/ssl_basic_SUITE.erl
@@ -50,6 +50,7 @@
%%--------------------------------------------------------------------
init_per_suite(Config0) ->
Dog = ssl_test_lib:timetrap(?LONG_TIMEOUT *2),
+ catch crypto:stop(),
try crypto:start() of
ok ->
application:start(public_key),
@@ -261,7 +262,8 @@ all() ->
no_reuses_session_server_restart_new_cert_file, reuseaddr,
hibernate, connect_twice, renegotiate_dos_mitigate_active,
renegotiate_dos_mitigate_passive,
- tcp_error_propagation_in_active_mode, rizzo, no_rizzo_rc4
+ tcp_error_propagation_in_active_mode, rizzo, no_rizzo_rc4,
+ recv_error_handling
].
groups() ->
@@ -3649,6 +3651,8 @@ no_reuses_session_server_restart_new_cert_file(Config) when is_list(Config) ->
ssl_test_lib:close(Server),
ssl_test_lib:close(Client0),
+ ssl:clear_pem_cache(),
+
NewServerOpts = new_config(PrivDir, DsaServerOpts),
Server1 =
@@ -3872,16 +3876,16 @@ tcp_error_propagation_in_active_mode(Config) when is_list(Config) ->
{ClientNode, ServerNode, Hostname} = ssl_test_lib:run_where(Config),
Server = ssl_test_lib:start_server([{node, ServerNode}, {port, 0},
- {from, self()},
- {mfa, {ssl_test_lib, no_result, []}},
- {options, ServerOpts}]),
+ {from, self()},
+ {mfa, {ssl_test_lib, no_result, []}},
+ {options, ServerOpts}]),
Port = ssl_test_lib:inet_port(Server),
{Client, #sslsocket{pid=Pid} = SslSocket} = ssl_test_lib:start_client([return_socket,
- {node, ClientNode}, {port, Port},
- {host, Hostname},
- {from, self()},
- {mfa, {?MODULE, receive_msg, []}},
- {options, ClientOpts}]),
+ {node, ClientNode}, {port, Port},
+ {host, Hostname},
+ {from, self()},
+ {mfa, {?MODULE, receive_msg, []}},
+ {options, ClientOpts}]),
{status, _, _, StatusInfo} = sys:get_status(Pid),
[_, _,_, _, Prop] = StatusInfo,
@@ -3892,6 +3896,32 @@ tcp_error_propagation_in_active_mode(Config) when is_list(Config) ->
Pid ! {tcp_error, Socket, etimedout},
ssl_test_lib:check_result(Client, {ssl_closed, SslSocket}).
+
+
+%%--------------------------------------------------------------------
+
+recv_error_handling(doc) ->
+ ["Special case of call error handling"];
+recv_error_handling(Config) when is_list(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, recv_close, []}},
+ {options, [{active, false} | ServerOpts]}]),
+ Port = ssl_test_lib:inet_port(Server),
+ {Client, #sslsocket{pid=Pid} = SslSocket} = ssl_test_lib:start_client([return_socket,
+ {node, ClientNode}, {port, Port},
+ {host, Hostname},
+ {from, self()},
+ {mfa, {ssl_test_lib, no_result, []}},
+ {options, ClientOpts}]),
+ ssl:close(SslSocket),
+ ssl_test_lib:check_result(Server, ok).
+
+
%%--------------------------------------------------------------------
rizzo(doc) -> ["Test that there is a 1/n-1-split for non RC4 in 'TLS < 1.1' as it is
@@ -3903,7 +3933,7 @@ rizzo(Config) when is_list(Config) ->
{?MODULE, send_recv_result_active_rizzo, []}),
run_send_recv_rizzo(Ciphers, Config, tlsv1,
{?MODULE, send_recv_result_active_rizzo, []}).
-
+%%--------------------------------------------------------------------
no_rizzo_rc4(doc) ->
["Test that there is no 1/n-1-split for RC4 as it is not vunrable to Rizzo/Dungon attack"];
@@ -3914,6 +3944,7 @@ no_rizzo_rc4(Config) when is_list(Config) ->
run_send_recv_rizzo(Ciphers, Config, tlsv1,
{?MODULE, send_recv_result_active_no_rizzo, []}).
+%%--------------------------------------------------------------------
run_send_recv_rizzo(Ciphers, Config, Version, Mfa) ->
Result = lists:map(fun(Cipher) ->
rizzo_test(Cipher, Config, Version, Mfa) end,
@@ -3967,6 +3998,15 @@ send_recv_result(Socket) ->
{ok,"Hello world"} = ssl:recv(Socket, 11),
ok.
+recv_close(Socket) ->
+ {error, closed} = ssl:recv(Socket, 11),
+ receive
+ {_,{error,closed}} ->
+ error_extra_close_sent_to_user_process
+ after 500 ->
+ ok
+ end.
+
send_recv_result_active(Socket) ->
ssl:send(Socket, "Hello world"),
receive
diff --git a/lib/ssl/test/ssl_dist_SUITE.erl b/lib/ssl/test/ssl_dist_SUITE.erl
index 12d92c8ca1..818f7f1897 100644
--- a/lib/ssl/test/ssl_dist_SUITE.erl
+++ b/lib/ssl/test/ssl_dist_SUITE.erl
@@ -369,7 +369,7 @@ mk_node_cmdline(ListenPort, Name, Args) ->
_ -> "-name "
end,
{ok, Pwd} = file:get_cwd(),
- Prog ++ " "
+ "\"" ++ Prog ++ "\" "
++ Static ++ " "
++ NameSw ++ " " ++ Name ++ " "
++ "-pa " ++ Pa ++ " "
@@ -729,7 +729,7 @@ add_ssl_opts_config(Config) ->
[{ssl_opts, "-boot " ++ Script} | Config]
catch
_:_ ->
- [{ssl_opts, "-pa " ++ filename:dirname(code:which(ssl))}
+ [{ssl_opts, "-pa \"" ++ filename:dirname(code:which(ssl))++"\""}
| add_comment_config(
"Bootscript wasn't used since the test wasn't run on an "
"installed OTP system.",
diff --git a/lib/ssl/test/ssl_packet_SUITE.erl b/lib/ssl/test/ssl_packet_SUITE.erl
index 4b74f57a60..593b1fda5e 100644
--- a/lib/ssl/test/ssl_packet_SUITE.erl
+++ b/lib/ssl/test/ssl_packet_SUITE.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2008-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2008-2012. 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
@@ -53,6 +53,7 @@
%% variable, but should NOT alter/remove any existing entries.
%%--------------------------------------------------------------------
init_per_suite(Config) ->
+ catch crypto:stop(),
try crypto:start() of
ok ->
application:start(public_key),
diff --git a/lib/ssl/test/ssl_payload_SUITE.erl b/lib/ssl/test/ssl_payload_SUITE.erl
index 24e86b3913..02b5516e35 100644
--- a/lib/ssl/test/ssl_payload_SUITE.erl
+++ b/lib/ssl/test/ssl_payload_SUITE.erl
@@ -37,6 +37,7 @@
%% variable, but should NOT alter/remove any existing entries.
%%--------------------------------------------------------------------
init_per_suite(Config) ->
+ catch crypto:stop(),
try crypto:start() of
ok ->
application:start(public_key),
diff --git a/lib/ssl/test/ssl_session_cache_SUITE.erl b/lib/ssl/test/ssl_session_cache_SUITE.erl
index 491aa893c2..6d758ecb01 100644
--- a/lib/ssl/test/ssl_session_cache_SUITE.erl
+++ b/lib/ssl/test/ssl_session_cache_SUITE.erl
@@ -49,6 +49,7 @@
%%--------------------------------------------------------------------
init_per_suite(Config0) ->
Dog = ssl_test_lib:timetrap(?LONG_TIMEOUT *2),
+ catch crypto:stop(),
try crypto:start() of
ok ->
application:start(public_key),
diff --git a/lib/ssl/test/ssl_to_openssl_SUITE.erl b/lib/ssl/test/ssl_to_openssl_SUITE.erl
index 01fca1f166..f593c1c552 100644
--- a/lib/ssl/test/ssl_to_openssl_SUITE.erl
+++ b/lib/ssl/test/ssl_to_openssl_SUITE.erl
@@ -50,6 +50,7 @@ init_per_suite(Config0) ->
false ->
{skip, "Openssl not found"};
_ ->
+ catch crypto:stop(),
try crypto:start() of
ok ->
application:start(public_key),
@@ -112,6 +113,9 @@ special_init(TestCase, Config)
special_init(ssl2_erlang_server_openssl_client, Config) ->
check_sane_openssl_sslv2(Config);
+special_init(ciphers_dsa_signed_certs, Config) ->
+ check_sane_openssl_dsa(Config);
+
special_init(_, Config) ->
Config.
@@ -600,7 +604,7 @@ erlang_server_openssl_client_no_wrap_sequence_number(Config) when is_list(Config
{from, self()},
{mfa, {ssl_test_lib,
trigger_renegotiate, [[Data, N+2]]}},
- {options, [{renegotiate_at, N} | ServerOpts]}]),
+ {options, [{renegotiate_at, N}, {reuse_sessions, false} | ServerOpts]}]),
Port = ssl_test_lib:inet_port(Server),
Cmd = "openssl s_client -port " ++ integer_to_list(Port) ++
@@ -1440,14 +1444,24 @@ check_sane_openssl_renegotaite(Config) ->
{skip, "Known renegotiation bug in OppenSSL"};
"OpenSSL 0.9.7" ++ _ ->
{skip, "Known renegotiation bug in OppenSSL"};
+ "OpenSSL 1.0.1c" ++ _ ->
+ {skip, "Known renegotiation bug in OppenSSL"};
_ ->
Config
end.
check_sane_openssl_sslv2(Config) ->
case os:cmd("openssl version") of
- "OpenSSL 1.0.0" ++ _ ->
+ "OpenSSL 1." ++ _ ->
{skip, "sslv2 by default turned of in 1.*"};
_ ->
Config
end.
+
+check_sane_openssl_dsa(Config) ->
+ case os:cmd("openssl version") of
+ "OpenSSL 1.0.1" ++ _ ->
+ {skip, "known dsa bug in openssl"};
+ _ ->
+ Config
+ end.
diff --git a/lib/stdlib/doc/src/Makefile b/lib/stdlib/doc/src/Makefile
index 6c92756ae7..c3138c4d9f 100644
--- a/lib/stdlib/doc/src/Makefile
+++ b/lib/stdlib/doc/src/Makefile
@@ -173,15 +173,15 @@ $(SPECDIR)/specs_erl_id_trans.xml:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/stdlib/doc/src/notes.xml b/lib/stdlib/doc/src/notes.xml
index 42a26ee44a..4834426d5c 100644
--- a/lib/stdlib/doc/src/notes.xml
+++ b/lib/stdlib/doc/src/notes.xml
@@ -30,6 +30,171 @@
</header>
<p>This document describes the changes made to the STDLIB application.</p>
+<section><title>STDLIB 1.18.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ References to <c>is_constant/1</c> (which was removed in
+ the R12 release) has been removed from documentation and
+ code.</p>
+ <p>
+ Own Id: OTP-6454 Aux Id: seq10407 </p>
+ </item>
+ <item>
+ <p>
+ Leave control back to gen_server during supervisor's
+ restart loop</p>
+ <p>
+ When an attempt to restart a child failed, supervisor
+ would earlier keep the execution flow and try to restart
+ the child over and over again until it either succeeded
+ or the restart frequency limit was reached. If none of
+ these happened, supervisor would hang forever in this
+ loop.</p>
+ <p>
+ This commit adds a timer of 0 ms where the control is
+ left back to the gen_server which implements the
+ supervisor. This way any incoming request to the
+ supervisor will be handled - which could help breaking
+ the infinite loop - e.g. shutdown request for the
+ supervisor or for the problematic child.</p>
+ <p>
+ This introduces some incompatibilities in stdlib due to
+ new return values from supervisor: <list>
+ <item>restart_child/2 can now return
+ {error,restarting}</item> <item>delete_child/2 can now
+ return {error,restarting}</item> <item>which_children/1
+ returns a list of {Id,Child,Type,Mods}, where Child, in
+ addition to the old pid() or 'undefined', now also can be
+ 'restarting'.</item> </list></p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9549</p>
+ </item>
+ <item>
+ <p>
+ If a temporary child's start function returned 'ignore',
+ then the supervisor would keep it's child specification.
+ This has been corrected. Child specifications for
+ non-existing temporary children shall never be kept.</p>
+ <p>
+ Own Id: OTP-9782 Aux Id: seq11964 </p>
+ </item>
+ <item>
+ <p> Use universal time as base in error logger
+ <p>
+ Previous conversion used the deprecated
+ calendar:local_time_to_universal_time/1 </p></p>
+ <p>
+ Own Id: OTP-9854</p>
+ </item>
+ <item>
+ <p>Calling a guard test (such as is_list/1) from the
+ top-level in a guard, would cause a compiler crash if
+ there was a local definition with the same name.
+ Corrected to reject the program with an error
+ message.</p>
+ <p>
+ Own Id: OTP-9866</p>
+ </item>
+ <item>
+ <p>
+ Fix the type spec from the doc of binary:part/3 (Thanks
+ to Ricardo Catalinas Jim�nez)</p>
+ <p>
+ Own Id: OTP-9920</p>
+ </item>
+ <item>
+ <p>
+ Correct spelling of registered (Thanks to Richard
+ Carlsson)</p>
+ <p>
+ Own Id: OTP-9925</p>
+ </item>
+ <item>
+ <p>
+ Put gb_trees documentation into alphabetical order
+ (Thanks to Aidan Hobson Sayers)</p>
+ <p>
+ Own Id: OTP-9929</p>
+ </item>
+ <item>
+ <p>
+ Fix bug in ETS with <c>compressed</c> option and
+ insertion of term containing large integers (>2G) on
+ 64-bit machines. Seen to cause emulator crash. (Thanks to
+ Diego Llarrull for excellent bug report)</p>
+ <p>
+ Own Id: OTP-9932</p>
+ </item>
+ <item>
+ <p>
+ Add plugin support for alternative name lookup This patch
+ introduces a new way of locating a behaviour instance:
+ {via, Module, Name}. (Thanks to Ulf Wiger)</p>
+ <p>
+ Own Id: OTP-9945</p>
+ </item>
+ <item>
+ <p> The function <c>digraph_utils:condensation/1</c> used
+ to create a digraph containing loops contradicting the
+ documentation which states that the created digraph is
+ free of cycles. This bug has been fixed. (Thanks to
+ Kostis Sagonas for finding the bug.) </p>
+ <p>
+ Own Id: OTP-9953</p>
+ </item>
+ <item>
+ <p> When an escript ends now all printout to standard
+ output and standard error gets out on the terminal. This
+ bug has been corrected by changing the behaviour of
+ erlang:halt/0,1, which should fix the same problem for
+ other escript-like applications, i.e that data stored in
+ the output port driver buffers got lost when printing on
+ a TTY and exiting through erlang:halt/0,1. </p>
+ <p> The BIF:s erlang:halt/0,1 has gotten improved
+ semantics and there is a new BIF erlang:halt/2 to
+ accomplish something like the old semantics. See the
+ documentation. </p>
+ <p> Now erlang:halt/0 and erlang:halt/1 with an integer
+ argument will close all ports and allow all pending async
+ threads operations to finish before exiting the emulator.
+ Previously erlang:halt/0 and erlang:halt(0) would just
+ wait for pending async threads operations but not close
+ ports. And erlang:halt/1 with a non-zero integer argument
+ would not even wait for pending async threads operations.
+ </p>
+ <p> To roughly the old behaviour, to not wait for ports
+ and async threads operations when you exit the emulator,
+ you use erlang:halt/2 with an integer first argument and
+ an option list containing {flush,false} as the second
+ argument. Note that now is flushing not dependant of the
+ exit code, and you can not only flush async threads
+ operations which we deemed as a strange behaviour anyway.
+ </p>
+ <p>Also, erlang:halt/1,2 has gotten a new feature: If the
+ first argument is the atom 'abort' the emulator is
+ aborted producing a core dump, if the operating system so
+ allows. </p>
+ <p>
+ Own Id: OTP-9985</p>
+ </item>
+ <item>
+ <p>
+ Add escript win32 alternative invocation. escript can now
+ be started as both "escript.exe" and "escript" (Thanks to
+ Pierre Rouleau)</p>
+ <p>
+ Own Id: OTP-9997</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>STDLIB 1.18</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/stdlib/examples/Makefile b/lib/stdlib/examples/Makefile
index 25c88d1de3..198aceb3a9 100644
--- a/lib/stdlib/examples/Makefile
+++ b/lib/stdlib/examples/Makefile
@@ -47,6 +47,6 @@ RELSYSDIR = $(RELEASE_PATH)/lib/stdlib-$(STDLIB_VSN)/examples
EXAMPLES = erl_id_trans.erl
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(EXAMPLES) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EXAMPLES) "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/stdlib/src/Makefile b/lib/stdlib/src/Makefile
index 90e239b00f..8bdaae57fd 100644
--- a/lib/stdlib/src/Makefile
+++ b/lib/stdlib/src/Makefile
@@ -198,13 +198,13 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) erl_parse.yrl $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) erl_parse.yrl "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/stdlib/src/filelib.erl b/lib/stdlib/src/filelib.erl
index d532cea187..b098d4cb91 100644
--- a/lib/stdlib/src/filelib.erl
+++ b/lib/stdlib/src/filelib.erl
@@ -264,6 +264,9 @@ ensure_dir(F) ->
case do_is_dir(Dir, file) of
true ->
ok;
+ false when Dir =:= F ->
+ %% Protect against infinite loop
+ {error,einval};
false ->
ensure_dir(Dir),
case file:make_dir(Dir) of
diff --git a/lib/stdlib/src/lib.erl b/lib/stdlib/src/lib.erl
index 314fd60903..cf4b87d7eb 100644
--- a/lib/stdlib/src/lib.erl
+++ b/lib/stdlib/src/lib.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 1996-2011. All Rights Reserved.
+%% Copyright Ericsson AB 1996-2012. 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
@@ -209,7 +209,7 @@ explain_reason(badarg, error, [], _PF, _S) ->
explain_reason({badarg,V}, error=Cl, [], PF, S) -> % orelse, andalso
format_value(V, <<"bad argument: ">>, Cl, PF, S);
explain_reason(badarith, error, [], _PF, _S) ->
- <<"bad argument in an arithmetic expression">>;
+ <<"an error occurred when evaluating an arithmetic expression">>;
explain_reason({badarity,{Fun,As}}, error, [], _PF, _S)
when is_function(Fun) ->
%% Only the arity is displayed, not the arguments As.
diff --git a/lib/stdlib/test/Makefile b/lib/stdlib/test/Makefile
index 4de6ea3ee7..29b8e28d3a 100644
--- a/lib/stdlib/test/Makefile
+++ b/lib/stdlib/test/Makefile
@@ -135,10 +135,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) stdlib.spec $(EMAKEFILE) \
- $(ERL_FILES) $(COVERFILE) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(ERL_FILES) $(COVERFILE) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/stdlib/test/escript_SUITE.erl b/lib/stdlib/test/escript_SUITE.erl
index 9f95df062b..7ed1ee742a 100644
--- a/lib/stdlib/test/escript_SUITE.erl
+++ b/lib/stdlib/test/escript_SUITE.erl
@@ -62,7 +62,7 @@ end_per_group(_GroupName, Config) ->
Config.
init_per_testcase(_Case, Config) ->
- ?line Dog = ?t:timetrap(?t:minutes(1)),
+ ?line Dog = ?t:timetrap(?t:minutes(2)),
[{watchdog,Dog}|Config].
end_per_testcase(_Case, Config) ->
diff --git a/lib/stdlib/test/ets_SUITE.erl b/lib/stdlib/test/ets_SUITE.erl
index 954d19a46f..297c4ec1c9 100644
--- a/lib/stdlib/test/ets_SUITE.erl
+++ b/lib/stdlib/test/ets_SUITE.erl
@@ -715,30 +715,17 @@ adjust_xmem([T1,T2,T3,T4], {A0,B0,C0,D0} = _Mem0) ->
TabDiff = ?TAB_STRUCT_SZ,
Mem1 = {A0+TabDiff, B0+TabDiff, C0+TabDiff, D0+TabDiff},
- Mem2 = case {erlang:system_info({wordsize,internal}),erlang:system_info({wordsize,external})} of
- %% Halfword, corrections for regular pointers occupying two internal words.
- {4,8} ->
- {A1,B1,C1,D1} = Mem1,
- {A1+4*ets:info(T1, size)+?DB_TREE_STACK_NEED,
- B1+3*ets:info(T2, size)+?DB_HASH_SIZEOF_EXTSEG,
- C1+3*ets:info(T3, size)+?DB_HASH_SIZEOF_EXTSEG,
- D1+3*ets:info(T4, size)+?DB_HASH_SIZEOF_EXTSEG};
- _ ->
- Mem1
- end,
-
- %% Adjust for hybrid and shared heaps:
- %% Each record is one word smaller.
- %%Mem2 = case erlang:system_info(heap_type) of
- %% private ->
- %% Mem1;
- %% _ ->
- %% {A1,B1,C1,D1} = Mem1,
- %% {A1-ets:info(T1, size),B1-ets:info(T2, size),
- %% C1-ets:info(T3, size),D1-ets:info(T4, size)}
- %% end,
- %%{Mem2,{ets:info(T1,stats),ets:info(T2,stats),ets:info(T3,stats),ets:info(T4,stats)}}.
- Mem2.
+ case {erlang:system_info({wordsize,internal}),erlang:system_info({wordsize,external})} of
+ %% Halfword, corrections for regular pointers occupying two internal words.
+ {4,8} ->
+ {A1,B1,C1,D1} = Mem1,
+ {A1+4*ets:info(T1, size)+?DB_TREE_STACK_NEED,
+ B1+3*ets:info(T2, size)+?DB_HASH_SIZEOF_EXTSEG,
+ C1+3*ets:info(T3, size)+?DB_HASH_SIZEOF_EXTSEG,
+ D1+3*ets:info(T4, size)+?DB_HASH_SIZEOF_EXTSEG};
+ _ ->
+ Mem1
+ end.
t_whitebox(doc) ->
["Diverse whitebox testes"];
diff --git a/lib/stdlib/test/io_proto_SUITE.erl b/lib/stdlib/test/io_proto_SUITE.erl
index 9bed20f771..661d57c85b 100644
--- a/lib/stdlib/test/io_proto_SUITE.erl
+++ b/lib/stdlib/test/io_proto_SUITE.erl
@@ -137,7 +137,7 @@ unicode_prompt(Config) when is_list(Config) ->
{putline, "io:get_line('')."},
{putline, "hej"},
{getline, "<<\"hej\\n\">>"}
- ],[],[],"-pa "++ PA),
+ ],[],[],"-pa \""++ PA++"\""),
%% And one with oldshell
?line rtnode([{putline,""},
{putline, "2."},
@@ -153,7 +153,7 @@ unicode_prompt(Config) when is_list(Config) ->
{putline, "io:get_line('')."},
{putline, "hej"},
{getline_re, ".*<<\"hej\\\\n\">>"}
- ],[],[],"-oldshell -pa "++PA),
+ ],[],[],"-oldshell -pa \""++PA++"\""),
ok.
@@ -732,7 +732,7 @@ bc_with_r12_1(Config) ->
PA = filename:dirname(code:which(?MODULE)),
Name1 = io_proto_r12_1,
?line N1 = list_to_atom(atom_to_list(Name1) ++ "@" ++ hostname()),
- ?line ?t:start_node(Name1, peer, [{args, "-pz "++PA},{erl,[{release,"r12b"}]}]),
+ ?line ?t:start_node(Name1, peer, [{args, "-pz \""++PA++"\""},{erl,[{release,"r12b"}]}]),
DataDir = ?config(data_dir,Config),
%PrivDir = ?config(priv_dir,Config),
FileName1 = filename:join([DataDir,"testdata_latin1.dat"]),
@@ -908,7 +908,7 @@ bc_with_r12_gl_1(_Config,Machine) ->
PA = filename:dirname(code:which(?MODULE)),
Name1 = io_proto_r12_gl_1,
?line N1 = list_to_atom(atom_to_list(Name1) ++ "@" ++ hostname()),
- ?line ?t:start_node(Name1, peer, [{args, "-pz "++PA},{erl,[{release,"r12b"}]}]),
+ ?line ?t:start_node(Name1, peer, [{args, "-pz \""++PA++"\""},{erl,[{release,"r12b"}]}]),
TestDataLine1 = [229,228,246],
TestDataLine1BinUtf = unicode:characters_to_binary(TestDataLine1),
TestDataLine1BinLatin = list_to_binary(TestDataLine1),
@@ -1290,7 +1290,7 @@ eof_on_pipe(Config) when is_list(Config) ->
end
end,
CommandLine1 = EchoLine ++
- Erl++" -noshell -eval "
+ "\""++Erl++"\" -noshell -eval "
"'io:format(\"~p\",[io:get_line(\"\")]),"
"io:format(\"~p\",[io:get_line(\"\")]),"
"io:format(\"~p\",[io:get_line(\"\")]).' -run init stop",
@@ -1301,7 +1301,7 @@ eof_on_pipe(Config) when is_list(Config) ->
exit({unexpected1,Other1})
end,
CommandLine2 = EchoLine ++
- Erl++" -noshell -eval "
+ "\""++Erl++"\" -noshell -eval "
"'io:setopts([binary]),io:format(\"~p\",[io:get_line(\"\")]),"
"io:format(\"~p\",[io:get_line(\"\")]),"
"io:format(\"~p\",[io:get_line(\"\")]).' -run init stop",
@@ -1340,7 +1340,8 @@ rtnode(Commands,Nodename,ErlPrefix,Extra) ->
?line {skip, Reason2};
Tempdir ->
?line SPid =
- start_runerl_node(RunErl,ErlPrefix++Erl,
+ start_runerl_node(RunErl,ErlPrefix++
+ "\\\""++Erl++"\\\"",
Tempdir,Nodename, Extra),
?line CPid = start_toerl_server(ToErl,Tempdir),
?line erase(getline_skipped),
@@ -1607,10 +1608,10 @@ start_runerl_node(RunErl,Erl,Tempdir,Nodename,Extra) ->
" "++Extra
end,
spawn(fun() ->
- ?dbg(RunErl++" "++Tempdir++"/ "++Tempdir++" \""++
- Erl++XArg++XXArg++"\""),
- os:cmd(RunErl++" "++Tempdir++"/ "++Tempdir++" \""++
- Erl++XArg++XXArg++"\"")
+ ?dbg("\""++RunErl++"\" "++Tempdir++"/ "++Tempdir++
+ " \""++Erl++XArg++XXArg++"\""),
+ os:cmd("\""++RunErl++"\" "++Tempdir++"/ "++Tempdir++
+ " \""++Erl++XArg++XXArg++"\"")
end).
start_toerl_server(ToErl,Tempdir) ->
@@ -1640,7 +1641,7 @@ try_to_erl(Command, N) ->
end.
toerl_server(Parent,ToErl,Tempdir) ->
- Port = try_to_erl(ToErl++" "++Tempdir++"/ 2>/dev/null",8),
+ Port = try_to_erl("\""++ToErl++"\" "++Tempdir++"/ 2>/dev/null",8),
case Port of
P when is_port(P) ->
Parent ! {self(),started};
diff --git a/lib/stdlib/test/shell_SUITE.erl b/lib/stdlib/test/shell_SUITE.erl
index 5be14767fa..4b83e42ee0 100644
--- a/lib/stdlib/test/shell_SUITE.erl
+++ b/lib/stdlib/test/shell_SUITE.erl
@@ -153,7 +153,7 @@ start_restricted_from_shell(Config) when is_list(Config) ->
comm_err(<<"begin init:stop() end.">>),
?line "exception exit: restricted shell does not allow init:stop()" =
comm_err(<<"begin F = fun() -> init:stop() end, F() end.">>),
- ?line "exception error: bad argument in an arithmetic expression" =
+ ?line "exception error: an error occurred when evaluating an arithmetic expression" =
comm_err(<<"begin +a end.">>),
?line "exception exit: restricted shell does not allow a + b" =
comm_err(<<"begin a+b end.">>),
@@ -2359,7 +2359,7 @@ otp_6554(Config) when is_list(Config) ->
comm_err(<<"fun(X) -> not X end(a).">>),
?line "exception error: bad argument: a" =
comm_err(<<"fun(A, B) -> A orelse B end(a, b).">>),
- ?line "exception error: bad argument in an arithmetic expression" =
+ ?line "exception error: an error occurred when evaluating an arithmetic expression" =
comm_err(<<"math:sqrt(2)/round(math:sqrt(0)).">>),
?line "exception error: interpreted function with arity 1 called with no arguments" =
comm_err(<<"fun(V) -> V end().">>),
@@ -2478,9 +2478,9 @@ otp_6554(Config) when is_list(Config) ->
" receive {'EXIT', Pid, {{nocatch,foo},_}} -> ok end "
"end.">>),
- ?line "exception error: bad argument in an arithmetic expression" =
+ ?line "exception error: an error occurred when evaluating an arithmetic expression" =
comm_err(<<"begin catch_exception(true), 1/0 end.">>),
- ?line "exception error: bad argument in an arithmetic expression" =
+ ?line "exception error: an error occurred when evaluating an arithmetic expression" =
comm_err(<<"begin catch_exception(false), 1/0 end.">>),
?line "exception error: no function clause matching call to catch_exception/1" =
comm_err(<<"catch_exception(1).">>),
@@ -2637,7 +2637,7 @@ otp_8393(Config) when is_list(Config) ->
prompt_err(<<"shell:prompt_func('> ').">>),
?line _ = shell:prompt_func(default),
- ?line "exception error: bad argument in an arithmetic expression"++_ =
+ ?line "exception error: an error occurred when evaluating an arithmetic expression"++_ =
prompt_err(<<"shell:prompt_func({shell_SUITE,prompt4}).">>),
?line _ = shell:prompt_func(default),
@@ -2710,7 +2710,7 @@ prompt3(L) ->
integer_to_list(N).
prompt4(_L) ->
- erlang:apply({erlang,'/'}, [1,0]).
+ erlang:apply(fun erlang:'/'/2, [1,0]).
prompt5(_L) ->
[1050,1072,1082,1074,1086,32,1077,32,85,110,105,99,111,100,101,32,63].
diff --git a/lib/stdlib/vsn.mk b/lib/stdlib/vsn.mk
index 694d39ce9c..3df7495ec4 100644
--- a/lib/stdlib/vsn.mk
+++ b/lib/stdlib/vsn.mk
@@ -1 +1 @@
-STDLIB_VSN = 1.18.1
+STDLIB_VSN = 1.18.2
diff --git a/lib/syntax_tools/doc/src/Makefile b/lib/syntax_tools/doc/src/Makefile
index 291b3e3047..d1c6989bd9 100644
--- a/lib/syntax_tools/doc/src/Makefile
+++ b/lib/syntax_tools/doc/src/Makefile
@@ -125,13 +125,13 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/syntax_tools/doc/src/notes.xml b/lib/syntax_tools/doc/src/notes.xml
index b9ac587043..434a3e721e 100644
--- a/lib/syntax_tools/doc/src/notes.xml
+++ b/lib/syntax_tools/doc/src/notes.xml
@@ -31,6 +31,21 @@
<p>This document describes the changes made to the Syntax_Tools
application.</p>
+<section><title>Syntax_Tools 1.6.8</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>Minor suppressions and fixes of compilation
+ warnings</p>
+ <p>
+ Own Id: OTP-10016</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Syntax_Tools 1.6.7.2</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/syntax_tools/examples/Makefile b/lib/syntax_tools/examples/Makefile
index 7cfe9185c2..2724b0899b 100644
--- a/lib/syntax_tools/examples/Makefile
+++ b/lib/syntax_tools/examples/Makefile
@@ -49,8 +49,8 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(EXAMPLE_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/syntax_tools/src/Makefile b/lib/syntax_tools/src/Makefile
index bac138e95a..dca5e78be9 100644
--- a/lib/syntax_tools/src/Makefile
+++ b/lib/syntax_tools/src/Makefile
@@ -80,10 +80,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(OBJECTS) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(SOURCES) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(OBJECTS) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(SOURCES) "$(RELSYSDIR)/src"
release_docs_spec:
diff --git a/lib/syntax_tools/test/Makefile b/lib/syntax_tools/test/Makefile
index 3e31bdbd50..d4733b9a42 100644
--- a/lib/syntax_tools/test/Makefile
+++ b/lib/syntax_tools/test/Makefile
@@ -57,9 +57,9 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) syntax_tools.spec syntax_tools.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) syntax_tools.spec syntax_tools.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/syntax_tools/vsn.mk b/lib/syntax_tools/vsn.mk
index 962492befd..2b9a08e192 100644
--- a/lib/syntax_tools/vsn.mk
+++ b/lib/syntax_tools/vsn.mk
@@ -1 +1 @@
-SYNTAX_TOOLS_VSN = 1.6.7.2
+SYNTAX_TOOLS_VSN = 1.6.8
diff --git a/lib/test_server/doc/src/Makefile b/lib/test_server/doc/src/Makefile
index b32f3d3c59..3ce549f0e1 100644
--- a/lib/test_server/doc/src/Makefile
+++ b/lib/test_server/doc/src/Makefile
@@ -119,16 +119,16 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man6
- $(INSTALL_DATA) $(MAN6_FILES) $(RELEASE_PATH)/man/man6
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man6"
+ $(INSTALL_DATA) $(MAN6_FILES) "$(RELEASE_PATH)/man/man6"
release_spec:
diff --git a/lib/test_server/doc/src/notes.xml b/lib/test_server/doc/src/notes.xml
index d90ad2c4ed..3701066e56 100644
--- a/lib/test_server/doc/src/notes.xml
+++ b/lib/test_server/doc/src/notes.xml
@@ -32,6 +32,155 @@
<file>notes.xml</file>
</header>
+<section><title>Test_Server 3.5.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ After a test case timeout or abortion, the
+ end_per_testcase function executes on a new dedicated
+ process. The group leader for this process should be set
+ to the IO server for the test case, which was not done
+ properly. The result of this error was that no warnings
+ about end_per_testcase failing or timing out were ever
+ printed in the test case log. Also, help functions such
+ as e.g. test_server:stop_node/1, attempting to
+ synchronize with the IO server, would hang. The fault has
+ been corrected.</p>
+ <p>
+ Own Id: OTP-9666</p>
+ </item>
+ <item>
+ <p>
+ A deadlock situation could occur if Common Test is
+ forwarding error_handler printouts to Test Server at the
+ same time a new test case is starting. This error has
+ been fixed.</p>
+ <p>
+ Own Id: OTP-9894</p>
+ </item>
+ <item>
+ <p>
+ When a test case was killed because of a timetrap
+ timeout, the current location (suite, case and line) was
+ not printed correctly in the log files. This has been
+ corrected.</p>
+ <p>
+ Own Id: OTP-9930 Aux Id: seq12002 </p>
+ </item>
+ <item>
+ <p>
+ Test Server and Common Test would add new error handlers
+ with each test run and fail to remove previously added
+ ones. In the case of Test Server, this would only happen
+ if SASL was not running on the test node. This has been
+ fixed.</p>
+ <p>
+ Own Id: OTP-9941 Aux Id: seq12009 </p>
+ </item>
+ <item>
+ <p>
+ If a test case process was terminated due to an exit
+ signal from a linked process, Test Server failed to
+ report the correct name of the suite and case to the
+ framework. This has been corrected.</p>
+ <p>
+ Own Id: OTP-9958 Aux Id: OTP-9855 </p>
+ </item>
+ </list>
+ </section>
+
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>
+ A new optional feature has been introduced that enables
+ Common Test to generate priv_dir directory names that are
+ unique for each test case or config function. The name of
+ the option/flag is 'create_priv_dir' and it can be set to
+ value 'auto_per_run' (which is the default, existing,
+ behaviour), or 'auto_per_tc' or 'manual_per_tc'. If
+ 'auto_per_tc' is used, Test Server creates a dedicated
+ priv_dir automatically for each test case (which can be
+ very expensive in case of many and/or repeated cases). If
+ 'manual_per_tc' is used, the user needs to create the
+ priv_dir explicitly by calling the new function
+ ct:make_priv_dir/0.</p>
+ <p>
+ Own Id: OTP-9659 Aux Id: seq11930 </p>
+ </item>
+ <item>
+ <p>
+ A column for test case group name has been added to the
+ suite overview HTML log file.</p>
+ <p>
+ Own Id: OTP-9730 Aux Id: seq11952 </p>
+ </item>
+ <item>
+ <p>
+ It is now possible to use the post_end_per_testcase CT
+ hook function to print a comment for a test case in the
+ overview log file, even if the test case gets killed by a
+ timetrap or unknown exit signal, or if the
+ end_per_testcase function times out.</p>
+ <p>
+ Own Id: OTP-9855 Aux Id: seq11979 </p>
+ </item>
+ <item>
+ <p>
+ Common Test will now print error information (with a time
+ stamp) in the test case log file immediately when a test
+ case fails. This makes it easier to see when, in time,
+ the fault actually occured, and aid the job of locating
+ relevant trace and debug printouts in the log.</p>
+ <p>
+ Own Id: OTP-9904 Aux Id: seq11985, OTP-9900 </p>
+ </item>
+ <item>
+ <p>
+ Test Server has been modified to check the SASL
+ errlog_type parameter when receiving an error logger
+ event, so that it doesn't print reports of type that the
+ user has disabled.</p>
+ <p>
+ Own Id: OTP-9955 Aux Id: seq12013 </p>
+ </item>
+ <item>
+ <p>
+ If an application cannot be found by ts it is
+ automatically skipped when testing.</p>
+ <p>
+ Own Id: OTP-9971</p>
+ </item>
+ <item>
+ <p>
+ By specifying a user defined function ({M,F,A} or fun) as
+ timetrap value, either by means of an info function or by
+ calling ct:timetrap/1, it is now possible to set a
+ timetrap that will be triggered when the user function
+ returns.</p>
+ <p>
+ Own Id: OTP-9988 Aux Id: OTP-9501, seq11894 </p>
+ </item>
+ <item>
+ <p>
+ If the optional configuration functions init_per_suite/1
+ and end_per_suite/1 are not implemented in the test
+ suite, local Common Test versions of these functions are
+ called instead, and will be displayed in the overview log
+ file. Any printouts made by the pre- or
+ post_init_per_suite and pre- or post_end_per_suite hook
+ functions are saved in the log files for these functions.</p>
+ <p>
+ Own Id: OTP-9992</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Test_Server 3.5</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/test_server/src/Makefile b/lib/test_server/src/Makefile
index 4bc51873c2..a75855eaab 100644
--- a/lib/test_server/src/Makefile
+++ b/lib/test_server/src/Makefile
@@ -124,22 +124,22 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(INTERNAL_HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(INTERNAL_HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_tests_spec: opt
- $(INSTALL_DIR) $(RELEASE_PATH)/test_server
+ $(INSTALL_DIR) "$(RELEASE_PATH)/test_server"
$(INSTALL_DATA) $(ERL_FILES) $(TS_ERL_FILES) \
$(HRL_FILES) $(INTERNAL_HRL_FILES) $(TS_HRL_FILES) \
$(TS_TARGET_FILES) \
$(AUTOCONF_FILES) $(C_FILES) $(COVER_FILES) $(CONFIG) \
- $(RELEASE_PATH)/test_server
- $(INSTALL_SCRIPT) $(PROGRAMS) $(RELEASE_PATH)/test_server
+ "$(RELEASE_PATH)/test_server"
+ $(INSTALL_SCRIPT) $(PROGRAMS) "$(RELEASE_PATH)/test_server"
release_docs_spec:
diff --git a/lib/test_server/src/configure.in b/lib/test_server/src/configure.in
index 097853bcfc..77bc993ccd 100644
--- a/lib/test_server/src/configure.in
+++ b/lib/test_server/src/configure.in
@@ -108,7 +108,7 @@ AC_CHECK_HEADER(poll.h, AC_DEFINE(HAVE_POLL_H))
# for the system.
AC_MSG_CHECKING([system version (for dynamic loading)])
-system=`uname -s`-`uname -r`
+system=`./config.sub $host`
AC_MSG_RESULT($system)
# Step 2: check for existence of -ldl library. This is needed because
@@ -119,10 +119,9 @@ AC_CHECK_LIB(dl, dlopen, have_dl=yes, have_dl=no)
# Step 3: set configuration options based on system name and version.
SHLIB_LDLIBS=
-
fullSrcDir=`cd $srcdir; pwd`
case $system in
- Linux*)
+ *-linux-*)
SHLIB_CFLAGS="-fPIC"
SHLIB_SUFFIX=".so"
if test "$have_dl" = yes; then
@@ -136,7 +135,7 @@ case $system in
fi
SHLIB_EXTRACT_ALL=""
;;
- NetBSD-*|FreeBSD-*|OpenBSD-*|DragonFly*)
+ *-netbsd*|*-freebsd*|*-openbsd*|*-dragonfly*)
# Not available on all versions: check for include file.
AC_CHECK_HEADER(dlfcn.h, [
SHLIB_CFLAGS="-fpic"
@@ -153,28 +152,21 @@ case $system in
])
SHLIB_EXTRACT_ALL=""
;;
- SunOS-4*)
- SHLIB_CFLAGS="-PIC"
- SHLIB_LD="ld"
- SHLIB_LDFLAGS="$LDFLAGS"
- SHLIB_SUFFIX=".so"
- SHLIB_EXTRACT_ALL=""
- ;;
- SunOS-5*|UNIX_SV-4.2*)
+ *-solaris2*|*-sysv4*)
SHLIB_CFLAGS="-KPIC"
SHLIB_LD="/usr/ccs/bin/ld"
SHLIB_LDFLAGS="$LDFLAGS -G -z text"
SHLIB_SUFFIX=".so"
SHLIB_EXTRACT_ALL="-z allextract"
;;
- Darwin*)
+ *darwin*)
SHLIB_CFLAGS="-fno-common"
SHLIB_LD="cc"
SHLIB_LDFLAGS="$LDFLAGS -bundle -flat_namespace -undefined suppress"
SHLIB_SUFFIX=".so"
SHLIB_EXTRACT_ALL=""
;;
- OSF1*)
+ *osf1*)
SHLIB_CFLAGS="-fPIC"
SHLIB_LD="ld"
SHLIB_LDFLAGS="$LDFLAGS -shared"
@@ -206,19 +198,19 @@ esac
if test "$CC" = "gcc" -o `$CC -v 2>&1 | grep -c gcc` != "0" ; then
case $system in
- AIX-*)
+ *-aix)
;;
- BSD/OS*)
+ *-bsd*)
;;
- IRIX*)
+ *-irix)
;;
- NetBSD-*|FreeBSD-*|OpenBSD-*)
+ *-netbsd|*-freebsd|*-openbsd)
;;
- RISCos-*)
+ *-riscos)
;;
- ULTRIX-4.*)
+ *ultrix4.*)
;;
- Darwin*)
+ *darwin*)
;;
*)
SHLIB_CFLAGS="-fPIC"
diff --git a/lib/test_server/src/test_server_node.erl b/lib/test_server/src/test_server_node.erl
index e8498a43f2..6358efa764 100644
--- a/lib/test_server/src/test_server_node.erl
+++ b/lib/test_server/src/test_server_node.erl
@@ -407,7 +407,7 @@ start_node_peer(SlaveName, OptList, From, TI) ->
% Support for erl_crash_dump files..
CrashFile = filename:join([TI#target_info.test_server_dir,
"erl_crash_dump."++cast_to_list(SlaveName)]),
- CrashArgs = lists:concat([" -env ERL_CRASH_DUMP ",CrashFile," "]),
+ CrashArgs = lists:concat([" -env ERL_CRASH_DUMP \"",CrashFile,"\" "]),
FailOnError = start_node_get_option_value(fail_on_error, OptList, true),
Pa = TI#target_info.test_server_dir,
Prog0 = start_node_get_option_value(erl, OptList, default),
@@ -420,7 +420,7 @@ start_node_peer(SlaveName, OptList, From, TI) ->
Cmd = lists:concat([Prog,
" -detached ",
TI#target_info.naming, " ", SlaveName,
- " -pa ", Pa,
+ " -pa \"", Pa,"\"",
NodeStarted,
CrashArgs,
" ", Args]),
@@ -472,9 +472,9 @@ start_node_slave(SlaveName, OptList, From, TI) ->
CrashFile = filename:join([TI#target_info.test_server_dir,
"erl_crash_dump."++cast_to_list(SlaveName)]),
- CrashArgs = lists:concat([" -env ERL_CRASH_DUMP ",CrashFile," "]),
+ CrashArgs = lists:concat([" -env ERL_CRASH_DUMP \"",CrashFile,"\" "]),
Pa = TI#target_info.test_server_dir,
- Args = lists:concat([" -pa ", Pa, " ", SuppliedArgs, CrashArgs]),
+ Args = lists:concat([" -pa \"", Pa, "\" ", SuppliedArgs, CrashArgs]),
Prog0 = start_node_get_option_value(erl, OptList, default),
Prog = pick_erl_program(Prog0),
diff --git a/lib/test_server/src/ts.erl b/lib/test_server/src/ts.erl
index cb06264adb..4899f38d2b 100644
--- a/lib/test_server/src/ts.erl
+++ b/lib/test_server/src/ts.erl
@@ -27,9 +27,10 @@
-export([run/0, run/1, run/2, run/3, run/4,
clean/0, clean/1,
tests/0, tests/1,
- install/0, install/1, install/2, index/0,
+ install/0, install/1, index/0,
estone/0, estone/1,
cross_cover_analyse/1,
+ compile_testcases/0, compile_testcases/1,
help/0]).
-export([i/0, l/1, r/0, r/1, r/2, r/3]).
@@ -88,35 +89,25 @@
-define(
install_help,
[
- " ts:install() - Install TS for local target with no Options.\n"
- " ts:install([Options])\n",
- " - Install TS for local target with Options\n"
- " ts:install({Architecture, Target_name})\n",
- " - Install TS for a remote target architecture.\n",
- " and target network name (e.g. {vxworks_cpu32, sauron}).\n",
- " ts:install({Architecture, Target_name}, [Options])\n",
- " - Install TS as above, and with Options.\n",
+ " ts:install() - Install TS with no Options.\n"
+ " ts:install([Options]) - Install TS with Options\n"
"\n",
"Installation options supported:\n",
" {longnames, true} - Use fully qualified hostnames\n",
- " {hosts, [HostList]}\n"
- " - Use theese hosts for distributed testing.\n"
" {verbose, Level} - Sets verbosity level for TS output (0,1,2), 0 is\n"
" quiet(default).\n"
- " {slavetargets, SlaveTarges}\n"
- " - Available hosts for starting slave nodes for\n"
- " platforms which cannot have more than one erlang\n"
- " node per host.\n"
- " {crossroot, TargetErlRoot}\n"
- " - Erlang root directory on target host\n"
- " Mandatory for remote targets\n"
- " {master, {MasterHost, MasterCookie}}\n"
- " - Master host and cookie for targets which are\n"
- " started as slave nodes.\n"
- " erl_boot_server must be started on master before\n"
- " test is run.\n"
- " Optional, default is controller host and then\n"
- " erl_boot_server is started autmatically\n"
+ " {crossroot, ErlTop}\n"
+ " - Erlang root directory on build host, ~n"
+ " normally same value as $ERL_TOP\n"
+ " {crossenv, [{Key,Val}]}\n"
+ " - Environmentals used by test configure on build host\n"
+ " {crossflags, FlagsString}\n"
+ " - Flags used by test configure on build host\n"
+ " {xcomp, XCompFile}\n"
+ " - The xcomp file to use for cross compiling the~n"
+ " testcases. Using this option will override any~n"
+ " cross* configurations given to ts. Note that you~n"
+ " have to have a correct ERL_TOP as well.~n"
]).
help() ->
@@ -183,26 +174,24 @@ help(installed) ->
" cover_details. Analyses modules specified in\n"
" cross.cover.\n"
" Level can be 'overview' or 'details'.\n",
+ " ts:compile_testcases()~n"
+ " ts:compile_testcases(Apps)~n"
+ " - Compile all testcases for usage in a cross ~n"
+ " compile environment."
" \n"
"Installation (already done):\n"
],
show_help([H,?install_help]).
show_help(H) ->
- io:put_chars(lists:flatten(H)).
+ io:format(lists:flatten(H)).
%% Installs tests.
install() ->
ts_install:install(install_local,[]).
-install({Architecture, Target_name}) ->
- ts_install:install({ts_lib:maybe_atom_to_list(Architecture),
- ts_lib:maybe_atom_to_list(Target_name)}, []);
install(Options) when is_list(Options) ->
ts_install:install(install_local,Options).
-install({Architecture, Target_name}, Options) when is_list(Options)->
- ts_install:install({ts_lib:maybe_atom_to_list(Architecture),
- ts_lib:maybe_atom_to_list(Target_name)}, Options).
%% Updates the local index page.
@@ -728,3 +717,23 @@ cover_type(cover_details) -> details.
do_load(Mod) ->
code:purge(Mod),
code:load_file(Mod).
+
+
+compile_testcases() ->
+ compile_datadirs("../*/*_data").
+
+compile_testcases(App) when is_atom(App) ->
+ compile_testcases([App]);
+compile_testcases([App | T]) ->
+ compile_datadirs(io_lib:format("../~s_test/*_data", [App])),
+ compile_testcases(T);
+compile_testcases([]) ->
+ ok.
+
+compile_datadirs(DataDirs) ->
+ {ok,Variables} = file:consult("variables"),
+
+ lists:foreach(fun(Dir) ->
+ ts_lib:make_non_erlang(Dir, Variables)
+ end,
+ filelib:wildcard(DataDirs)).
diff --git a/lib/test_server/src/ts.hrl b/lib/test_server/src/ts.hrl
index 885a726c54..db804d23a1 100644
--- a/lib/test_server/src/ts.hrl
+++ b/lib/test_server/src/ts.hrl
@@ -28,6 +28,7 @@
-define(run_summary, "suite.summary").
-define(cover_total,"total_cover.log").
-define(variables, "variables").
+-define(cross_variables, "variables-cross").
-define(LF, [10]). % Newline in VxWorks script
-define(CHAR_PER_LINE, 60). % Characters per VxWorks script building line
-define(CROSS_COOKIE, "cross"). % cookie used when cross platform testing
diff --git a/lib/test_server/src/ts_autoconf_win32.erl b/lib/test_server/src/ts_autoconf_win32.erl
index 9103542fd2..258040b39e 100644
--- a/lib/test_server/src/ts_autoconf_win32.erl
+++ b/lib/test_server/src/ts_autoconf_win32.erl
@@ -67,6 +67,7 @@ system_type(Vars) ->
{5,1,_} -> "Windows XP";
{5,2,_} -> "Windows 2003";
{6,0,_} -> "Windows Vista";
+ {6,1,_} -> "Windows 7";
{_,_,_} -> "Windows NCC-1701-D"
end;
{win32, windows} ->
diff --git a/lib/test_server/src/ts_erl_config.erl b/lib/test_server/src/ts_erl_config.erl
index 5585e8ccd3..45d88016a4 100644
--- a/lib/test_server/src/ts_erl_config.erl
+++ b/lib/test_server/src/ts_erl_config.erl
@@ -128,15 +128,15 @@ erts_lib(Vars,OsType) ->
ErtsLibInternal}
end,
[{erts_lib_include,
- filename:nativename(ErtsLibInclude)},
+ quote(filename:nativename(ErtsLibInclude))},
{erts_lib_include_generated,
- filename:nativename(ErtsLibIncludeGenerated)},
+ quote(filename:nativename(ErtsLibIncludeGenerated))},
{erts_lib_include_internal,
- filename:nativename(ErtsLibIncludeInternal)},
+ quote(filename:nativename(ErtsLibIncludeInternal))},
{erts_lib_include_internal_generated,
- filename:nativename(ErtsLibIncludeInternalGenerated)},
- {erts_lib_path, filename:nativename(ErtsLibPath)},
- {erts_lib_internal_path, filename:nativename(ErtsLibInternalPath)},
+ quote(filename:nativename(ErtsLibIncludeInternalGenerated))},
+ {erts_lib_path, quote(filename:nativename(ErtsLibPath))},
+ {erts_lib_internal_path, quote(filename:nativename(ErtsLibInternalPath))},
{erts_lib_multi_threaded, erts_lib_name(multi_threaded, OsType)},
{erts_lib_single_threaded, erts_lib_name(single_threaded, OsType)}
| Vars].
@@ -145,13 +145,13 @@ erl_include(Vars) ->
Include =
case erl_root(Vars) of
{installed, Root} ->
- filename:join([Root, "usr", "include"]);
+ quote(filename:join([Root, "usr", "include"]));
{srctree, Root, Target} ->
- filename:join([Root, "erts", "emulator", "beam"])
- ++ " -I" ++ filename:join([Root, "erts", "emulator"])
+ quote(filename:join([Root, "erts", "emulator", "beam"]))
+ ++ " -I" ++ quote(filename:join([Root, "erts", "emulator"]))
++ system_include(Root, Vars)
- ++ " -I" ++ filename:join([Root, "erts", "include"])
- ++ " -I" ++ filename:join([Root, "erts", "include", Target])
+ ++ " -I" ++ quote(filename:join([Root, "erts", "include"]))
+ ++ " -I" ++ quote(filename:join([Root, "erts", "include", Target]))
end,
[{erl_include, filename:nativename(Include)}|Vars].
@@ -163,7 +163,7 @@ system_include(Root, Vars) ->
"VxWorks" -> "sys.vxworks";
_ -> "sys/unix"
end,
- " -I" ++ filename:nativename(filename:join([Root, "erts", "emulator", SysDir])).
+ " -I" ++ quote(filename:nativename(filename:join([Root, "erts", "emulator", SysDir]))).
erl_interface(Vars,OsType) ->
{Incl, {LibPath, MkIncl}} =
@@ -220,20 +220,16 @@ erl_interface(Vars,OsType) ->
_ ->
"" % VxWorks
end,
- CrossCompile = case OsType of
- vxworks -> "true";
- _ -> "false"
- end,
- [{erl_interface_libpath, filename:nativename(LibPath)},
+ [{erl_interface_libpath, quote(filename:nativename(LibPath))},
{erl_interface_sock_libs, sock_libraries(OsType)},
{erl_interface_lib, Lib},
{erl_interface_eilib, Lib1},
{erl_interface_lib_drv, LibDrv},
{erl_interface_eilib_drv, Lib1Drv},
{erl_interface_threadlib, ThreadLib},
- {erl_interface_include, filename:nativename(Incl)},
- {erl_interface_mk_include, filename:nativename(MkIncl)},
- {erl_interface_cross_compile, CrossCompile} | Vars].
+ {erl_interface_include, quote(filename:nativename(Incl))},
+ {erl_interface_mk_include, quote(filename:nativename(MkIncl))}
+ | Vars].
ic(Vars, OsType) ->
{ClassPath, LibPath, Incl} =
@@ -250,10 +246,10 @@ ic(Vars, OsType) ->
end,
filename:join(Dir, "include")}
end,
- [{ic_classpath, filename:nativename(ClassPath)},
- {ic_libpath, filename:nativename(LibPath)},
+ [{ic_classpath, quote(filename:nativename(ClassPath))},
+ {ic_libpath, quote(filename:nativename(LibPath))},
{ic_lib, link_library("ic", OsType)},
- {ic_include_path, filename:nativename(Incl)}|Vars].
+ {ic_include_path, quote(filename:nativename(Incl))}|Vars].
jinterface(Vars, _OsType) ->
ClassPath =
@@ -263,7 +259,7 @@ jinterface(Vars, _OsType) ->
Dir ->
filename:join([Dir, "priv", "OtpErlang.jar"])
end,
- [{jinterface_classpath, filename:nativename(ClassPath)}|Vars].
+ [{jinterface_classpath, quote(filename:nativename(ClassPath))}|Vars].
lib_dir(Vars, Lib) ->
LibLibDir = case Lib of
@@ -276,8 +272,6 @@ lib_dir(Vars, Lib) ->
case {get_var(crossroot, Vars), LibLibDir} of
{{error, _}, _} -> %no crossroot
LibLibDir;
- {_, {error, _}} -> %no lib
- LibLibDir;
{CrossRoot, _} ->
%% XXX: Ugly. So ugly I won't comment it
%% /Patrik
@@ -299,18 +293,16 @@ lib_dir(Vars, Lib) ->
end.
erl_root(Vars) ->
- Root = code:root_dir(),
- case ts_lib:erlang_type() of
+ Root = case get_var(crossroot,Vars) of
+ {error, notfound} -> code:root_dir();
+ CrossRoot -> CrossRoot
+ end,
+ case ts_lib:erlang_type(Root) of
{srctree, _Version} ->
Target = get_var(target, Vars),
{srctree, Root, Target};
{_, _Version} ->
- case get_var(crossroot,Vars) of
- {error, notfound} ->
- {installed, Root};
- CrossRoot ->
- {installed, CrossRoot}
- end
+ {installed, Root}
end.
@@ -362,10 +354,17 @@ ssl(Vars, _OsType) ->
{error, bad_name} ->
throw({cannot_find_app, ssl});
Dir ->
- [{ssl_libdir, filename:nativename(Dir)}| Vars]
+ [{ssl_libdir, quote(filename:nativename(Dir))}| Vars]
end.
separators(Vars, {win32,_}) ->
[{'DS',"\\"},{'PS',";"}|Vars];
separators(Vars, _) ->
[{'DS',"/"},{'PS',":"}|Vars].
+
+quote([$ |R]) ->
+ "\\ "++quote(R);
+quote([C|R]) ->
+ [C|quote(R)];
+quote([]) ->
+ [].
diff --git a/lib/test_server/src/ts_install.erl b/lib/test_server/src/ts_install.erl
index 9703478f20..99ccfbc9bc 100644
--- a/lib/test_server/src/ts_install.erl
+++ b/lib/test_server/src/ts_install.erl
@@ -28,12 +28,25 @@ install(install_local, Options) ->
install(os:type(), Options);
install(TargetSystem, Options) ->
- io:format("Running configure for cross architecture, network target name~n"
- "~p~n", [TargetSystem]),
- case autoconf(TargetSystem) of
+ case file:consult(?variables) of
+ {ok, Vars} ->
+ case proplists:get_value(cross,Vars) of
+ "yes" when Options == []->
+ target_install(Vars);
+ _ ->
+ build_install(TargetSystem, Options)
+ end;
+ _ ->
+ build_install(TargetSystem, Options)
+ end.
+
+
+build_install(TargetSystem, Options) ->
+ XComp = parse_xcomp_file(proplists:get_value(xcomp,Options)),
+ case autoconf(TargetSystem, XComp++Options) of
{ok, Vars0} ->
OsType = os_type(TargetSystem),
- Vars1 = ts_erl_config:variables(merge(Vars0,Options),OsType),
+ Vars1 = ts_erl_config:variables(Vars0++XComp++Options,OsType),
{Options1, Vars2} = add_vars(Vars1, Options),
Vars3 = lists:flatten([Options1|Vars2]),
write_terms(?variables, Vars3);
@@ -45,32 +58,43 @@ os_type({unix,_}=OsType) -> OsType;
os_type({win32,_}=OsType) -> OsType;
os_type(_Other) -> vxworks.
-merge(Vars,[]) ->
- Vars;
-merge(Vars,[{crossroot,X}| Tail]) ->
- merge([{crossroot, X} | Vars], Tail);
-merge(Vars,[_X | Tail]) ->
- merge(Vars,Tail).
+target_install(CrossVars) ->
+ io:format("Cross installation detected, skipping configure and data_dir make~n"),
+ case file:rename(?variables,?cross_variables) of
+ ok ->
+ ok;
+ _ ->
+ io:format("Could not find variables file from cross make~n"),
+ throw(cross_installation_failed)
+ end,
+ CPU = proplists:get_value('CPU',CrossVars),
+ OS = proplists:get_value(os,CrossVars),
+ {Options,Vars} = add_vars([{cross,"yes"},{'CPU',CPU},{os,OS}],[]),
+ Variables = lists:flatten([Options|Vars]),
+ write_terms(?variables, Variables).
%% Autoconf for various platforms.
%% unix uses the configure script
%% win32 uses ts_autoconf_win32
%% VxWorks uses ts_autoconf_vxworks.
-autoconf(TargetSystem) ->
- case autoconf1(TargetSystem) of
+autoconf(TargetSystem, XComp) ->
+ case autoconf1(TargetSystem, XComp) of
ok ->
autoconf2(file:read_file("conf_vars"));
Error ->
Error
end.
-autoconf1({win32, _}) ->
+autoconf1({win32, _},[{cross,"no"}]) ->
ts_autoconf_win32:configure();
-autoconf1({unix, _}) ->
- unix_autoconf();
-autoconf1(Other) ->
- ts_autoconf_vxworks:configure(Other).
+autoconf1({unix, _},XCompFile) ->
+ unix_autoconf(XCompFile);
+autoconf1(Other,[{cross,"no"}]) ->
+ ts_autoconf_vxworks:configure(Other);
+autoconf1(_,_) ->
+ io:format("cross compilation not supported for that this platform~n"),
+ throw(cross_installation_failed).
autoconf2({ok, Bin}) ->
get_vars(binary_to_list(Bin), name, [], []);
@@ -92,27 +116,40 @@ get_vars([], name, [], Result) ->
get_vars(_, _, _, _) ->
{error, fatal_bad_conf_vars}.
-unix_autoconf() ->
+unix_autoconf(XConf) ->
Configure = filename:absname("configure"),
- Args = case catch erlang:system_info(threads) of
- false -> "";
- _ -> " --enable-shlib-thread-safety"
- end
- ++ case catch string:str(erlang:system_info(system_version),
- "debug") > 0 of
- false -> "";
- _ -> " --enable-debug-mode"
- end,
+ Flags = proplists:get_value(crossflags,XConf,[]),
+ Env = proplists:get_value(crossenv,XConf,[]),
+ Host = get_xcomp_flag("host", Flags),
+ Build = get_xcomp_flag("build", Flags),
+ Threads = [" --enable-shlib-thread-safety" ||
+ erlang:system_info(threads) /= false],
+ Debug = [" --enable-debug-mode" ||
+ string:str(erlang:system_info(system_version),"debug") > 0],
+ Args = Host ++ Build ++ Threads ++ Debug,
case filelib:is_file(Configure) of
true ->
- Env = macosx_cflags(),
- Port = open_port({spawn, Configure ++ Args},
- [stream, eof, {env,Env}]),
+ OSXEnv = macosx_cflags(),
+ io:format("Running ~sEnv: ~p~n",
+ [lists:flatten(Configure ++ Args),Env++OSXEnv]),
+ Port = open_port({spawn, lists:flatten(["\"",Configure,"\"",Args])},
+ [stream, eof, {env,Env++OSXEnv}]),
ts_lib:print_data(Port);
false ->
{error, no_configure_script}
end.
+
+get_xcomp_flag(Flag, Flags) ->
+ get_xcomp_flag(Flag, Flag, Flags).
+get_xcomp_flag(Flag, Tag, Flags) ->
+ case proplists:get_value(Flag,Flags) of
+ undefined -> "";
+ "guess" -> [" --",Tag,"=",os:cmd("$ERL_TOP/erts/autoconf/config.guess")];
+ HostVal -> [" --",Tag,"=",HostVal]
+ end.
+
+
macosx_cflags() ->
case os:type() of
{unix, darwin} ->
@@ -125,10 +162,33 @@ macosx_cflags() ->
[]
end.
+parse_xcomp_file(undefined) ->
+ [{cross,"no"}];
+parse_xcomp_file(Filepath) ->
+ {ok,Bin} = file:read_file(Filepath),
+ Lines = binary:split(Bin,<<"\n">>,[global,trim]),
+ {Envs,Flags} = parse_xcomp_file(Lines,[],[]),
+ [{cross,"yes"},{crossroot,os:getenv("ERL_TOP")},
+ {crossenv,Envs},{crossflags,Flags}].
+
+parse_xcomp_file([<<A:8,_/binary>> = Line|R],Envs,Flags)
+ when $A =< A, A =< $Z ->
+ [Var,Value] = binary:split(Line,<<"=">>),
+ parse_xcomp_file(R,[{binary_to_list(Var),
+ binary_to_list(Value)}|Envs],Flags);
+parse_xcomp_file([<<"erl_xcomp_",Line/binary>>|R],Envs,Flags) ->
+ [Var,Value] = binary:split(Line,<<"=">>),
+ parse_xcomp_file(R,Envs,[{binary_to_list(Var),
+ binary_to_list(Value)}|Flags]);
+parse_xcomp_file([_|R],Envs,Flags) ->
+ parse_xcomp_file(R,Envs,Flags);
+parse_xcomp_file([],Envs,Flags) ->
+ {lists:reverse(Envs),lists:reverse(Flags)}.
+
write_terms(Name, Terms) ->
case file:open(Name, [write]) of
{ok, Fd} ->
- Result = write_terms1(Fd, Terms),
+ Result = write_terms1(Fd, remove_duplicates(Terms)),
file:close(Fd),
Result;
{error, Reason} ->
@@ -141,6 +201,17 @@ write_terms1(Fd, [Term|Rest]) ->
write_terms1(_, []) ->
ok.
+remove_duplicates(List) ->
+ lists:reverse(
+ lists:foldl(fun({Key,Val},Acc) ->
+ R = make_ref(),
+ case proplists:get_value(Key,Acc,R) of
+ R -> [{Key,Val}|Acc];
+ _Else ->
+ Acc
+ end
+ end,[],List)).
+
add_vars(Vars0, Opts0) ->
{Opts,LongNames} =
case lists:keymember(longnames, 1, Opts0) of
@@ -209,12 +280,11 @@ platform(Vars) ->
LC = lock_checking(),
MT = modified_timing(),
AsyncThreads = async_threads(),
- HeapType = heap_type_label(),
Debug = debug(),
CpuBits = word_size(),
Common = lists:concat([Hostname,"/",OsType,"/",CpuType,CpuBits,LinuxDist,
Schedulers,BindType,KP,IOTHR,LC,MT,AsyncThreads,
- HeapType,Debug,ExtraLabel]),
+ Debug,ExtraLabel]),
PlatformId = lists:concat([ErlType, " ", Version, Common]),
PlatformLabel = ErlType ++ Common,
PlatformFilename = platform_as_filename(PlatformId),
@@ -272,12 +342,6 @@ hostname() ->
"/localhost"
end.
-heap_type_label() ->
- case catch erlang:system_info(heap_type) of
- hybrid -> "/Hybrid";
- _ -> "" %private
- end.
-
async_threads() ->
case catch erlang:system_info(threads) of
true -> "/A"++integer_to_list(erlang:system_info(thread_pool_size));
diff --git a/lib/test_server/src/ts_install_cth.erl b/lib/test_server/src/ts_install_cth.erl
index a41916fd0a..67f2df0cae 100644
--- a/lib/test_server/src/ts_install_cth.erl
+++ b/lib/test_server/src/ts_install_cth.erl
@@ -95,17 +95,12 @@ pre_init_per_suite(_Suite,Config,State) ->
try
{ok,Variables} =
file:consult(filename:join(State#state.ts_conf_dir,"variables")),
-
- %% Make the stuff in all_SUITE_data if it exists
- AllDir = filename:join(DataDir,"../all_SUITE_data"),
- case filelib:is_dir(AllDir) of
- true ->
- make_non_erlang(AllDir,Variables);
- false ->
- ok
+ case proplists:get_value(cross,Variables) of
+ "yes" ->
+ ct:log("Not making data dir as tests have been cross compiled");
+ _ ->
+ ts_lib:make_non_erlang(DataDir, Variables)
end,
-
- make_non_erlang(DataDir, Variables),
{add_node_name(Config, State), State}
catch Error:Reason ->
@@ -219,39 +214,6 @@ terminate(_State) ->
%%% ============================================================================
%%% Local functions
%%% ============================================================================
-%% Configure and run all the Makefiles in the data dirs of the suite
-%% in question
-make_non_erlang(DataDir, Variables) ->
- {ok,CurrWD} = file:get_cwd(),
- try
- file:set_cwd(DataDir),
- MakeCommand = proplists:get_value(make_command,Variables),
-
- FirstMakefile = filename:join(DataDir,"Makefile.first"),
- case filelib:is_regular(FirstMakefile) of
- true ->
- ct:log("Making ~p",[FirstMakefile]),
- ok = ts_make:make(
- MakeCommand, DataDir, filename:basename(FirstMakefile));
- false ->
- ok
- end,
-
- MakefileSrc = filename:join(DataDir,"Makefile.src"),
- MakefileDest = filename:join(DataDir,"Makefile"),
- case filelib:is_regular(MakefileSrc) of
- true ->
- ok = ts_lib:subst_file(MakefileSrc,MakefileDest,Variables),
- ct:log("Making ~p",[MakefileDest]),
- ok = ts_make:make([{makefile,"Makefile"},{data_dir,DataDir}
- | Variables]);
- false ->
- ok
- end
- after
- file:set_cwd(CurrWD),
- timer:sleep(100)
- end.
%% Add a nodename to config if it does not exist
add_node_name(Config, State) ->
diff --git a/lib/test_server/src/ts_lib.erl b/lib/test_server/src/ts_lib.erl
index 2f0a4ea8c0..d521d2beda 100644
--- a/lib/test_server/src/ts_lib.erl
+++ b/lib/test_server/src/ts_lib.erl
@@ -24,10 +24,12 @@
%% Avoid warning for local function error/1 clashing with autoimported BIF.
-compile({no_auto_import,[error/1]}).
-export([error/1, var/2, erlang_type/0,
+ erlang_type/1,
initial_capital/1, interesting_logs/1,
specs/1, suites/2, last_test/1,
force_write_file/2, force_delete/1,
subst_file/3, subst/2, print_data/1,
+ make_non_erlang/2,
maybe_atom_to_list/1, progress/4
]).
@@ -73,8 +75,10 @@ progress(Vars, Level, Format, Args) ->
%% Returns: {Type, Version} where Type is otp|src
erlang_type() ->
+ erlang_type(code:root_dir()).
+erlang_type(RootDir) ->
{_, Version} = init:script_id(),
- RelDir = filename:join(code:root_dir(), "releases"), % Only in installed
+ RelDir = filename:join(RootDir, "releases"), % Only in installed
case filelib:is_file(RelDir) of
true -> {otp,Version}; % installed OTP
false -> {srctree,Version} % source code tree
@@ -333,3 +337,45 @@ maybe_atom_to_list(To_list) when is_list(To_list) ->
maybe_atom_to_list(To_list) when is_atom(To_list)->
atom_to_list(To_list).
+
+%% Configure and run all the Makefiles in the data dir of the suite
+%% in question
+make_non_erlang(DataDir, Variables) ->
+ %% Make the stuff in all_SUITE_data if it exists
+ AllDir = filename:join(DataDir,"../all_SUITE_data"),
+ case filelib:is_dir(AllDir) of
+ true ->
+ make_non_erlang_do(AllDir,Variables);
+ false ->
+ ok
+ end,
+ make_non_erlang_do(DataDir, Variables).
+
+make_non_erlang_do(DataDir, Variables) ->
+ try
+ MakeCommand = proplists:get_value(make_command,Variables),
+
+ FirstMakefile = filename:join(DataDir,"Makefile.first"),
+ case filelib:is_regular(FirstMakefile) of
+ true ->
+ io:format("Making ~p",[FirstMakefile]),
+ ok = ts_make:make(
+ MakeCommand, DataDir, filename:basename(FirstMakefile));
+ false ->
+ ok
+ end,
+
+ MakefileSrc = filename:join(DataDir,"Makefile.src"),
+ MakefileDest = filename:join(DataDir,"Makefile"),
+ case filelib:is_regular(MakefileSrc) of
+ true ->
+ ok = ts_lib:subst_file(MakefileSrc,MakefileDest,Variables),
+ io:format("Making ~p",[MakefileDest]),
+ ok = ts_make:make([{makefile,"Makefile"},{data_dir,DataDir}
+ | Variables]);
+ false ->
+ ok
+ end
+ after
+ timer:sleep(100) %% maybe unnecessary now when we don't do set_cwd anymore
+ end.
diff --git a/lib/test_server/src/ts_make.erl b/lib/test_server/src/ts_make.erl
index 3df66111a3..1d8ef230c7 100644
--- a/lib/test_server/src/ts_make.erl
+++ b/lib/test_server/src/ts_make.erl
@@ -25,12 +25,12 @@
%% Functions to be called from make test cases.
make(Config) when is_list(Config) ->
- DataDir = ?config(data_dir, Config),
- Makefile = ?config(makefile, Config),
- Make = ?config(make_command, Config),
+ DataDir = proplists:get_value(data_dir, Config),
+ Makefile = proplists:get_value(makefile, Config),
+ Make = proplists:get_value(make_command, Config),
case make(Make, DataDir, Makefile) of
ok -> ok;
- {error,Reason} -> ?t:fail({make_failed,Reason})
+ {error,Reason} -> exit({make_failed,Reason})
end.
unmake(Config) when is_list(Config) ->
@@ -85,7 +85,7 @@ run_make_script({win32, _}, Make, Dir, Makefile) ->
{"run_make.bat",
".\\run_make",
["@echo off\r\n",
- "cd ", filename:nativename(Dir), "\r\n",
+ "cd \"", filename:nativename(Dir), "\"\r\n",
Make, " -f ", Makefile, " \r\n",
"if errorlevel 1 echo *error*\r\n",
"if not errorlevel 1 echo *ok*\r\n"]};
@@ -93,7 +93,7 @@ run_make_script({unix, _}, Make, Dir, Makefile) ->
{"run_make",
"/bin/sh ./run_make",
["#!/bin/sh\n",
- "cd ", Dir, "\n",
+ "cd \"", Dir, "\"\n",
Make, " -f ", Makefile, " 2>&1\n",
"case $? in\n",
" 0) echo '*ok*';;\n",
diff --git a/lib/test_server/src/ts_run.erl b/lib/test_server/src/ts_run.erl
index 885a3c9b96..a61028e4bc 100644
--- a/lib/test_server/src/ts_run.erl
+++ b/lib/test_server/src/ts_run.erl
@@ -229,7 +229,7 @@ make_command(Vars, Spec, State) ->
%% uncomment the line below to disable exception formatting
%% " -test_server_format_exception false",
" -boot start_sasl -sasl errlog_type error",
- " -pz ",Cwd,
+ " -pz \"",Cwd,"\"",
" -ct_test_vars ",TestVars,
" -eval \"file:set_cwd(\\\"",TestDir,"\\\")\" "
" -eval \"ct:run_test(",
diff --git a/lib/test_server/test/Makefile b/lib/test_server/test/Makefile
index 198440bb17..b2ac95afaa 100644
--- a/lib/test_server/test/Makefile
+++ b/lib/test_server/test/Makefile
@@ -83,10 +83,10 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) $(COVERFILE) $(RELSYSDIR)
- $(INSTALL_DATA) test_server_test_lib.hrl test_server.spec test_server.cover $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(EMAKEFILE) $(ERL_FILES) $(COVERFILE) "$(RELSYSDIR)"
+ $(INSTALL_DATA) test_server_test_lib.hrl test_server.spec test_server.cover "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/toolbar/doc/src/Makefile b/lib/toolbar/doc/src/Makefile
index 76147c111e..af907859d7 100644
--- a/lib/toolbar/doc/src/Makefile
+++ b/lib/toolbar/doc/src/Makefile
@@ -102,14 +102,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/toolbar/doc/src/notes.xml b/lib/toolbar/doc/src/notes.xml
index ac6ad533fc..b901e6c8ff 100644
--- a/lib/toolbar/doc/src/notes.xml
+++ b/lib/toolbar/doc/src/notes.xml
@@ -31,6 +31,26 @@
<p>This document describes the changes made to the Toolbar
application.</p>
+<section><title>Toolbar 1.4.2.2</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Toolbar 1.4.2.1</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/toolbar/src/Makefile b/lib/toolbar/src/Makefile
index 14e1451609..91ce305e26 100644
--- a/lib/toolbar/src/Makefile
+++ b/lib/toolbar/src/Makefile
@@ -84,10 +84,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/toolbar/vsn.mk b/lib/toolbar/vsn.mk
index b2b0764877..9fbfec871f 100644
--- a/lib/toolbar/vsn.mk
+++ b/lib/toolbar/vsn.mk
@@ -1,4 +1,4 @@
-TOOLBAR_VSN = 1.4.2.1
+TOOLBAR_VSN = 1.4.2.2
diff --git a/lib/tools/c_src/Makefile.in b/lib/tools/c_src/Makefile.in
index b8c4aed6e2..0382d3228d 100644
--- a/lib/tools/c_src/Makefile.in
+++ b/lib/tools/c_src/Makefile.in
@@ -188,11 +188,11 @@ include ../vsn.mk
RELSYSDIR = $(RELEASE_PATH)/lib/tools-$(TOOLS_VSN)
release_spec: all
- $(INSTALL_DIR) $(RELSYSDIR)/c_src
- $(INSTALL_DATA) $(EMEM_SRCS) $(EMEM_HEADERS) $(RELSYSDIR)/c_src
+ $(INSTALL_DIR) "$(RELSYSDIR)/c_src"
+ $(INSTALL_DATA) $(EMEM_SRCS) $(EMEM_HEADERS) "$(RELSYSDIR)/c_src"
ifneq ($(PROGS),)
- $(INSTALL_DIR) $(RELSYSDIR)/bin
- $(INSTALL_PROGRAM) $(PROGS) $(RELSYSDIR)/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/bin"
+ $(INSTALL_PROGRAM) $(PROGS) "$(RELSYSDIR)/bin"
endif
release_docs_spec:
diff --git a/lib/tools/doc/src/Makefile b/lib/tools/doc/src/Makefile
index 433f123ae5..a76ce98ad6 100644
--- a/lib/tools/doc/src/Makefile
+++ b/lib/tools/doc/src/Makefile
@@ -121,14 +121,14 @@ clean clean_docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/tools/doc/src/eprof.xml b/lib/tools/doc/src/eprof.xml
index 8b614d8860..1c5e38109b 100644
--- a/lib/tools/doc/src/eprof.xml
+++ b/lib/tools/doc/src/eprof.xml
@@ -67,9 +67,9 @@
<p><c>Rootset</c> is a list of pids and registered names.</p>
<p>The function returns <c>profiling</c> if tracing could be enabled
for all processes in <c>Rootset</c>, or <c>error</c> otherwise.</p>
- <p>A pattern can be selected to narrow the profiling. For instance ca a specific
- module be selected and only the code processes executes in that module will be
- profiled.</p>
+ <p>A pattern can be selected to narrow the profiling. For instance a
+ specific module can be selected, and only the code executed in that
+ module will be profiled.</p>
</desc>
</func>
<func>
@@ -147,8 +147,8 @@
</type>
<desc>
<p>This function ensures that the results displayed by
- <c>analyze/0,1,2</c> are printed both to
- the file <c>File</c> and the screen.</p>
+ <c>analyze/0,1,2</c> are printed both to the file
+ <c>File</c> and the screen.</p>
</desc>
</func>
<func>
diff --git a/lib/tools/doc/src/notes.xml b/lib/tools/doc/src/notes.xml
index e24e1c5977..f4da132102 100644
--- a/lib/tools/doc/src/notes.xml
+++ b/lib/tools/doc/src/notes.xml
@@ -30,6 +30,31 @@
</header>
<p>This document describes the changes made to the Tools application.</p>
+<section><title>Tools 2.6.7</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Makefiles in erts, hipe and tools have been corrected to
+ enable parallel make, i.e MAKEFLAGS=-jX where X is the
+ parallelity number. As a result of this dependencies were
+ corrected since that is what is needed for parallel make
+ to work.</p>
+ <p>
+ Own Id: OTP-9857 Aux Id: OTP-9451 </p>
+ </item>
+ <item>
+ <p>Minor suppressions and fixes of compilation
+ warnings</p>
+ <p>
+ Own Id: OTP-10016</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Tools 2.6.6.6</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/tools/emacs/Makefile b/lib/tools/emacs/Makefile
index 8533488463..e5ed56b412 100644
--- a/lib/tools/emacs/Makefile
+++ b/lib/tools/emacs/Makefile
@@ -71,9 +71,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/emacs
+ $(INSTALL_DIR) "$(RELSYSDIR)/emacs"
$(INSTALL_DATA) $(EL_FILES) $(README_FILES) $(TEST_FILES) \
- $(RELSYSDIR)/emacs
+ "$(RELSYSDIR)/emacs"
ifeq ($(DOCTYPE),pdf)
release_docs_spec:
@@ -82,7 +82,7 @@ ifeq ($(DOCTYPE),ps)
release_docs_spec:
else
release_docs_spec: docs
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN_FILES) $(RELEASE_PATH)/man/man3
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN_FILES) "$(RELEASE_PATH)/man/man3"
endif
endif
diff --git a/lib/tools/emacs/erlang.el b/lib/tools/emacs/erlang.el
index bc7a190fb4..2f6c7f554e 100644
--- a/lib/tools/emacs/erlang.el
+++ b/lib/tools/emacs/erlang.el
@@ -2986,18 +2986,52 @@ This assumes that the preceding expression is either simple
(forward-sexp (- arg))
(let ((col (current-column)))
(skip-chars-backward " \t")
- ;; Needed to match the colon in "'foo':'bar'".
- (if (not (memq (preceding-char) '(?# ?:)))
- col
- ;; Special hack to handle: (note line break)
- ;; [#myrecord{
- ;; foo = foo}]
- (or
- (ignore-errors
- (backward-char 1)
- (forward-sexp -1)
- (current-column))
- col)))))
+ ;; Special hack to handle: (note line break)
+ ;; [#myrecord{
+ ;; foo = foo}]
+ ;; where the call (forward-sexp -1) will fail when point is at the `#'.
+ (or
+ (ignore-errors
+ ;; Needed to match the colon in "'foo':'bar'".
+ (cond ((eq (preceding-char) ?:)
+ (backward-char 1)
+ (forward-sexp -1)
+ (current-column))
+ ((eq (preceding-char) ?#)
+ ;; We may now be at:
+ ;; - either a construction of a new record
+ ;; - or update of a record, in which case we want
+ ;; the column of the expression to be updated.
+ ;;
+ ;; To see which of the two cases we are at, we first
+ ;; move an expression backwards, check for keywords,
+ ;; then immediately an expression forwards. Moving
+ ;; backwards skips past tokens like `,' or `->', but
+ ;; when moving forwards again, we won't skip past such
+ ;; tokens. We use this: if, after having moved
+ ;; forwards, we're back where we started, then it was
+ ;; a record update.
+ ;; The check for keywords is to detect cases like:
+ ;; case Something of #record_construction{...}
+ (backward-char 1)
+ (let ((record-start (point))
+ (record-start-col (current-column)))
+ (forward-sexp -1)
+ (let ((preceding-expr-col (current-column))
+ ;; white space definition according to erl_scan
+ (white-space "\000-\040\200-\240"))
+ (if (erlang-at-keyword)
+ ;; The (forward-sexp -1) call moved past a keyword
+ (1+ record-start-col)
+ (forward-sexp 1)
+ (skip-chars-forward white-space record-start)
+ ;; Are we back where we started? If so, it was an update.
+ (if (= (point) record-start)
+ preceding-expr-col
+ (goto-char record-start)
+ (1+ (current-column)))))))
+ (t col)))
+ col))))
(defun erlang-indent-parenthesis (stack-position)
(let ((previous (erlang-indent-find-preceding-expr)))
diff --git a/lib/tools/emacs/test.erl.indented b/lib/tools/emacs/test.erl.indented
index 2948ccf1b5..e0593c6522 100644
--- a/lib/tools/emacs/test.erl.indented
+++ b/lib/tools/emacs/test.erl.indented
@@ -657,3 +657,41 @@ indent_comprehensions() ->
foo() ->
[#foo{
foo = foo}].
+
+%% Record indentation
+some_function_with_a_very_long_name() ->
+ #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b},
+ case dummy_function_with_a_very_very_long_name(x) of
+ #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b} ->
+ ok;
+ Var = #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b} ->
+ Var#'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b};
+ #xyz{
+ a=1,
+ b=2} ->
+ ok
+ end.
+
+another_function_with_a_very_very_long_name() ->
+ #rec{
+ field1=1,
+ field2=1}.
+
+some_function_name_xyz(xyzzy, #some_record{
+ field1=Field1,
+ field2=Field2}) ->
+ SomeVariable = f(#'Some-long-record-name'{
+ field_a = 1,
+ 'inter-xyz-parameters' =
+ #'Some-other-very-long-record-name'{
+ field2 = Field1,
+ field2 = Field2}}),
+ {ok, SomeVariable}.
diff --git a/lib/tools/emacs/test.erl.orig b/lib/tools/emacs/test.erl.orig
index 1221c5655e..69356aca9e 100644
--- a/lib/tools/emacs/test.erl.orig
+++ b/lib/tools/emacs/test.erl.orig
@@ -657,3 +657,41 @@ ok.
foo() ->
[#foo{
foo = foo}].
+
+%% Record indentation
+some_function_with_a_very_long_name() ->
+ #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b},
+ case dummy_function_with_a_very_very_long_name(x) of
+ #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b} ->
+ ok;
+ Var = #'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b} ->
+ Var#'a-long-record-name-like-it-sometimes-is-with-asn.1-records'{
+ field1=a,
+ field2=b};
+ #xyz{
+ a=1,
+ b=2} ->
+ ok
+ end.
+
+another_function_with_a_very_very_long_name() ->
+ #rec{
+ field1=1,
+ field2=1}.
+
+some_function_name_xyz(xyzzy, #some_record{
+ field1=Field1,
+ field2=Field2}) ->
+ SomeVariable = f(#'Some-long-record-name'{
+ field_a = 1,
+ 'inter-xyz-parameters' =
+ #'Some-other-very-long-record-name'{
+ field2 = Field1,
+ field2 = Field2}}),
+ {ok, SomeVariable}.
diff --git a/lib/tools/examples/Makefile b/lib/tools/examples/Makefile
index 9fb8434633..fc14ee54d6 100644
--- a/lib/tools/examples/Makefile
+++ b/lib/tools/examples/Makefile
@@ -50,7 +50,7 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/examples
- $(INSTALL_DATA) $(EXAMPLE_FILES) $(RELSYSDIR)/examples
+ $(INSTALL_DIR) "$(RELSYSDIR)/examples"
+ $(INSTALL_DATA) $(EXAMPLE_FILES) "$(RELSYSDIR)/examples"
release_docs_spec:
diff --git a/lib/tools/priv/Makefile b/lib/tools/priv/Makefile
index 6fea580c00..b32ba5820d 100644
--- a/lib/tools/priv/Makefile
+++ b/lib/tools/priv/Makefile
@@ -58,9 +58,9 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(HTDOCS_FILES) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(TOOL_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(HTDOCS_FILES) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(TOOL_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/tools/src/Makefile b/lib/tools/src/Makefile
index 360f4f8f29..4c0cc8cde7 100644
--- a/lib/tools/src/Makefile
+++ b/lib/tools/src/Makefile
@@ -105,10 +105,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(YRL_FILE) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) \
- $(RELSYSDIR)/ebin
+ "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/tools/src/fprof.erl b/lib/tools/src/fprof.erl
index 8165a6c13a..4cbb910f11 100644
--- a/lib/tools/src/fprof.erl
+++ b/lib/tools/src/fprof.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
-%% Copyright Ericsson AB 2001-2011. All Rights Reserved.
+%% Copyright Ericsson AB 2001-2012. 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
@@ -89,9 +89,7 @@ dbg(_, _, _) ->
apply({M, F}, Args)
when is_atom(M), is_atom(F), is_list(Args) ->
- Arity = length(Args),
- Function = fun M:F/Arity,
- apply_1(Function, Args, []);
+ apply_1(M, F, Args, []);
apply(Fun, Args)
when is_function(Fun), is_list(Args) ->
apply_1(Fun, Args, []);
@@ -99,26 +97,25 @@ apply(A, B) ->
erlang:error(badarg, [A, B]).
apply(M, F, Args) when is_atom(M), is_atom(F), is_list(Args) ->
- apply_1({M, F}, Args, []);
+ apply_1(M, F, Args, []);
apply({M, F}, Args, Options)
when is_atom(M), is_atom(F), is_list(Args), is_list(Options) ->
- Arity = length(Args),
- Function = fun M:F/Arity,
- apply_1(Function, Args, Options);
+ apply_1(M, F, Args, Options);
apply(Fun, Args, Options)
when is_function(Fun), is_list(Args), is_list(Options) ->
apply_1(Fun, Args, Options);
apply(A, B, C) ->
erlang:error(badarg, [A, B, C]).
-apply(Module, Function, Args, Options)
- when is_atom(Module), is_atom(Function), is_list(Args), is_list(Options) ->
- Arity = length(Args),
- Fun = fun Module:Function/Arity,
- apply_1(Fun, Args, Options);
+apply(M, F, Args, Options)
+ when is_atom(M), is_atom(F), is_list(Args), is_list(Options) ->
+ apply_1(M, F, Args, Options);
apply(A, B, C, D) ->
erlang:error(badarg, [A, B, C, D]).
+apply_1(M, F, Args, Options) ->
+ Arity = length(Args),
+ apply_1(fun M:F/Arity, Args, Options).
apply_1(Function, Args, Options) ->
{[_, Procs, Continue], Options_1} =
diff --git a/lib/tools/test/Makefile b/lib/tools/test/Makefile
index 8019b7269f..b9a42041a2 100644
--- a/lib/tools/test/Makefile
+++ b/lib/tools/test/Makefile
@@ -84,11 +84,11 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: make_emakefile
- $(INSTALL_DIR) $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
$(INSTALL_DATA) $(SPEC_FILES) $(COVER_FILE) $(EMAKEFILE) \
- $(ERL_FILES) $(RELSYSDIR)
- chmod -R u+w $(RELSYSDIR)
- @tar cf - *_SUITE_data | (cd $(RELSYSDIR); tar xf -)
+ $(ERL_FILES) "$(RELSYSDIR)"
+ chmod -R u+w "$(RELSYSDIR)"
+ @tar cf - *_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
release_docs_spec:
diff --git a/lib/tools/test/cover_SUITE.erl b/lib/tools/test/cover_SUITE.erl
index 576d7e261c..0cd53a05db 100644
--- a/lib/tools/test/cover_SUITE.erl
+++ b/lib/tools/test/cover_SUITE.erl
@@ -574,14 +574,7 @@ otp_5418(Config) when is_list(Config) ->
ok.
-otp_6115(suite) -> [];
otp_6115(Config) when is_list(Config) ->
- case erlang:system_info(heap_type) of
- hybrid -> {skip,"Hybrid-heap emulator doesn't keep track of funs"};
- _ -> otp_6115_1(Config)
- end.
-
-otp_6115_1(Config) ->
?line {ok, CWD} = file:get_cwd(),
?line Dir = filename:join(?config(data_dir, Config), otp_6115),
?line ok = file:set_cwd(Dir),
diff --git a/lib/tools/vsn.mk b/lib/tools/vsn.mk
index 269d3d7773..788ee12900 100644
--- a/lib/tools/vsn.mk
+++ b/lib/tools/vsn.mk
@@ -1 +1 @@
-TOOLS_VSN = 2.6.6.6
+TOOLS_VSN = 2.6.8
diff --git a/lib/tv/doc/src/Makefile b/lib/tv/doc/src/Makefile
index 21478d0931..e36dd84b73 100644
--- a/lib/tv/doc/src/Makefile
+++ b/lib/tv/doc/src/Makefile
@@ -125,14 +125,14 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/tv/doc/src/notes.xml b/lib/tv/doc/src/notes.xml
index 97c99e6202..9217c018e9 100644
--- a/lib/tv/doc/src/notes.xml
+++ b/lib/tv/doc/src/notes.xml
@@ -30,6 +30,26 @@
</header>
<p>This document describes the changes made to the TV application.</p>
+<section><title>TV 2.1.4.9</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>The GS applications is now deprecated and will be
+ removed in the R16 release. The following GS-based
+ applications have been superseded by the Observer
+ application and will removed in R16: Appmon, Pman,
+ Tv.</p>
+ <p>
+ *** POTENTIAL INCOMPATIBILITY ***</p>
+ <p>
+ Own Id: OTP-9907</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>TV 2.1.4.8</title>
<section><title>Improvements and New Features</title>
diff --git a/lib/tv/priv/Makefile b/lib/tv/priv/Makefile
index 69e3e32c8a..73ea8f4ee9 100644
--- a/lib/tv/priv/Makefile
+++ b/lib/tv/priv/Makefile
@@ -64,8 +64,8 @@ clean:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) $(TOOLBAR_FILES) $(RELSYSDIR)/priv
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) $(TOOLBAR_FILES) "$(RELSYSDIR)/priv"
release_docs_spec:
diff --git a/lib/tv/src/Makefile b/lib/tv/src/Makefile
index 457b9d38c4..f078e5dee1 100644
--- a/lib/tv/src/Makefile
+++ b/lib/tv/src/Makefile
@@ -126,10 +126,10 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/tv/vsn.mk b/lib/tv/vsn.mk
index 756aae2096..1bb8ca30f8 100644
--- a/lib/tv/vsn.mk
+++ b/lib/tv/vsn.mk
@@ -1 +1 @@
-TV_VSN = 2.1.4.8
+TV_VSN = 2.1.4.9
diff --git a/lib/typer/src/Makefile b/lib/typer/src/Makefile
index 620b3ebb69..c3fae0ad42 100644
--- a/lib/typer/src/Makefile
+++ b/lib/typer/src/Makefile
@@ -101,10 +101,10 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
$(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(YRL_FILES) \
- $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(INSTALL_FILES) $(RELSYSDIR)/ebin
+ "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(INSTALL_FILES) "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/typer/src/typer.erl b/lib/typer/src/typer.erl
index 6392f5765f..1e40b8926e 100644
--- a/lib/typer/src/typer.erl
+++ b/lib/typer/src/typer.erl
@@ -83,6 +83,7 @@ start() ->
{Args, Analysis} = process_cl_args(),
%% io:format("Args: ~p\n", [Args]),
%% io:format("Analysis: ~p\n", [Analysis]),
+ Timer = dialyzer_timing:init(false),
TrustedFiles = filter_fd(Args#args.trusted, [], fun is_erl_file/1),
Analysis2 = extract(Analysis, TrustedFiles),
All_Files = get_all_files(Args),
@@ -91,6 +92,7 @@ start() ->
Analysis4 = collect_info(Analysis3),
%% io:format("Final: ~p\n", [Analysis4#analysis.fms]),
TypeInfo = get_type_info(Analysis4),
+ dialyzer_timing:stop(Timer),
show_or_annotate(TypeInfo),
%% io:format("\nTyper analysis finished\n"),
erlang:halt(0).
@@ -181,7 +183,6 @@ get_type_info(#analysis{callgraph = CallGraph,
remove_external(CallGraph, PLT) ->
{StrippedCG0, Ext} = dialyzer_callgraph:remove_external(CallGraph),
- StrippedCG = dialyzer_callgraph:finalize(StrippedCG0),
case get_external(Ext, PLT) of
[] -> ok;
Externals ->
@@ -192,7 +193,7 @@ remove_external(CallGraph, PLT) ->
_ -> msg(io_lib:format(" Unknown types: ~p\n", [ExtTypes]))
end
end,
- StrippedCG.
+ StrippedCG0.
-spec get_external([{mfa(), mfa()}], plt()) -> [mfa()].
@@ -901,8 +902,9 @@ analyze_core_tree(Core, Records, SpecInfo, CbInfo, ExpTypes, Analysis, File) ->
MergedExpTypes = sets:union(ExpTypes, OldExpTypes),
CS6 = dialyzer_codeserver:insert_temp_exported_types(MergedExpTypes, CS5),
Ex_Funcs = [{0,F,A} || {_,_,{F,A}} <- cerl:module_exports(Tree)],
- TmpCG = Analysis#analysis.callgraph,
- CG = dialyzer_callgraph:scan_core_tree(Tree, TmpCG),
+ CG = Analysis#analysis.callgraph,
+ {V, E} = dialyzer_callgraph:scan_core_tree(Tree, CG),
+ dialyzer_callgraph:add_edges(E, V, CG),
Fun = fun analyze_one_function/2,
All_Defs = cerl:module_defs(Tree),
Acc = lists:foldl(Fun, #tmpAcc{file = File, module = Module}, All_Defs),
diff --git a/lib/webtool/doc/src/Makefile b/lib/webtool/doc/src/Makefile
index 7b86752738..32269e9424 100644
--- a/lib/webtool/doc/src/Makefile
+++ b/lib/webtool/doc/src/Makefile
@@ -112,16 +112,16 @@ debug opt:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man1
- $(INSTALL_DATA) $(MAN1_FILES) $(RELEASE_PATH)/man/man1
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DATA) $(MAN1_FILES) "$(RELEASE_PATH)/man/man1"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/webtool/priv/Makefile b/lib/webtool/priv/Makefile
index 6e1c6606fe..6af997c2bb 100644
--- a/lib/webtool/priv/Makefile
+++ b/lib/webtool/priv/Makefile
@@ -67,14 +67,14 @@ docs:
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DIR) $(RELSYSDIR)/priv/root
- $(INSTALL_DIR) $(RELSYSDIR)/priv/root/conf
- $(INSTALL_DIR) $(RELSYSDIR)/priv/root/doc
- $(INSTALL_DATA) $(HTDOCS_FILES) $(RELSYSDIR)/priv/root/doc
- $(INSTALL_DATA) $(WEBSERVER_CONFIG_FILES) $(RELSYSDIR)/priv/root/conf
- $(INSTALL_DIR) $(RELSYSDIR)/priv/bin
- $(INSTALL_SCRIPT) $(SCRIPTS) $(RELSYSDIR)/priv/bin
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/root"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/root/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/root/doc"
+ $(INSTALL_DATA) $(HTDOCS_FILES) "$(RELSYSDIR)/priv/root/doc"
+ $(INSTALL_DATA) $(WEBSERVER_CONFIG_FILES) "$(RELSYSDIR)/priv/root/conf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv/bin"
+ $(INSTALL_SCRIPT) $(SCRIPTS) "$(RELSYSDIR)/priv/bin"
release_docs_spec:
diff --git a/lib/webtool/src/Makefile b/lib/webtool/src/Makefile
index 62845cd370..45e8b2a6f0 100644
--- a/lib/webtool/src/Makefile
+++ b/lib/webtool/src/Makefile
@@ -87,11 +87,11 @@ $(APPUP_TARGET): $(APPUP_SRC) ../vsn.mk
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) \
- $(RELSYSDIR)/ebin
+ "$(RELSYSDIR)/ebin"
release_docs_spec:
diff --git a/lib/wx/c_src/Makefile.in b/lib/wx/c_src/Makefile.in
index ce7f4bf53e..1497ac4d16 100644
--- a/lib/wx/c_src/Makefile.in
+++ b/lib/wx/c_src/Makefile.in
@@ -176,10 +176,10 @@ $(TARGET_DIR)/erl_gl$(SO_EXT): $(GL_OBJECTS)
# ----------------------------------------------------
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/priv
- $(INSTALL_DATA) ../priv/erlang-logo32.png $(RELSYSDIR)/priv/
- $(INSTALL_DATA) ../priv/erlang-logo64.png $(RELSYSDIR)/priv/
- $(INSTALL_PROGRAM) $(TARGET_DIR)/wxe_driver$(SO_EXT) $(RELSYSDIR)/priv/
- $(INSTALL_PROGRAM) $(TARGET_DIR)/erl_gl$(SO_EXT) $(RELSYSDIR)/priv/
+ $(INSTALL_DIR) "$(RELSYSDIR)/priv"
+ $(INSTALL_DATA) ../priv/erlang-logo32.png "$(RELSYSDIR)/priv/"
+ $(INSTALL_DATA) ../priv/erlang-logo64.png "$(RELSYSDIR)/priv/"
+ $(INSTALL_PROGRAM) $(TARGET_DIR)/wxe_driver$(SO_EXT) "$(RELSYSDIR)/priv/"
+ $(INSTALL_PROGRAM) $(TARGET_DIR)/erl_gl$(SO_EXT) "$(RELSYSDIR)/priv/"
release_docs_spec:
diff --git a/lib/wx/configure.in b/lib/wx/configure.in
index b27e114a3d..8e5f696bc7 100755
--- a/lib/wx/configure.in
+++ b/lib/wx/configure.in
@@ -571,7 +571,7 @@ if test X"$WX_HAVE_STATIC_LIBS" = X"true" ; then
LIBS=$WX_LIBS_STATIC
fi
-AC_LINK_IFELSE([
+AC_LINK_IFELSE([AC_LANG_SOURCE([
#ifdef WIN32
# include <windows.h>
# include <gl/gl.h>
@@ -583,6 +583,7 @@ AC_LINK_IFELSE([
#include "wx/wx.h"
#include "wx/stc/stc.h"
#include "wx/glcanvas.h"
+ ])
class MyApp : public wxApp
{
diff --git a/lib/wx/doc/src/Makefile b/lib/wx/doc/src/Makefile
index 834f887076..4e6727b6a6 100644
--- a/lib/wx/doc/src/Makefile
+++ b/lib/wx/doc/src/Makefile
@@ -95,13 +95,13 @@ ref_man.xml: ref_man.xml.src
@echo "</application>" >> ref_man.xml
@echo
-$(ErlMods:%.erl=%.xml):
+$(ErlMods:%.erl=%.xml): ../../src/$(@:%.xml=%.erl)
escript $(DOCGEN)/priv/bin/xml_from_edoc.escript -def vsn $(VSN) -preprocess true -sort_functions false ../../src/$(@:%.xml=%.erl)
-$(GenMods:%.erl=%.xml):
+$(GenMods:%.erl=%.xml): ../../src/gen/$(@:%.xml=%.erl)
escript $(DOCGEN)/priv/bin/xml_from_edoc.escript -def vsn $(VSN) -i ../../src -preprocess true -sort_functions false ../../src/gen/$(@:%.xml=%.erl)
-$(XML_CHAPTER_FILES):
+$(XML_CHAPTER_FILES): ../overview.edoc
escript $(DOCGEN)/priv/bin/xml_from_edoc.escript -def vsn $(VSN) -chapter ../overview.edoc
debug opt:
@@ -120,14 +120,14 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3_FILES) $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3_FILES) "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/wx/doc/src/notes.xml b/lib/wx/doc/src/notes.xml
index 4a94227a55..1ba7e62d7d 100644
--- a/lib/wx/doc/src/notes.xml
+++ b/lib/wx/doc/src/notes.xml
@@ -31,6 +31,23 @@
<p>This document describes the changes made to the wxErlang
application.</p>
+<section><title>Wx 0.99.2</title>
+
+ <section><title>Improvements and New Features</title>
+ <list>
+ <item>
+ <p>Fix errors in wxDC and wxGraphicsContext api.</p>
+ <p>Add wxTaskBarIcon.</p> <p>Add
+ wxStyledTextControl:setEdgeMode/2.</p> <p>Add type and
+ specs for all functions and records.</p>
+ <p>
+ Own Id: OTP-9947</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Wx 0.99.1</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/wx/examples/demo/Makefile b/lib/wx/examples/demo/Makefile
index 872723fb98..c60e9c3d50 100644
--- a/lib/wx/examples/demo/Makefile
+++ b/lib/wx/examples/demo/Makefile
@@ -69,7 +69,7 @@ docs:
run: opt
erl -smp -detached -pa $(TOPDIR)/ebin -s demo
-EXRELSYSDIR = $(RELSYSDIR)/examples/demo
+EXRELSYSDIR = "$(RELSYSDIR)/examples/demo"
include $(ERL_TOP)/make/otp_release_targets.mk
docs:
diff --git a/lib/wx/examples/simple/Makefile b/lib/wx/examples/simple/Makefile
index 0178aea890..3f2bf01556 100644
--- a/lib/wx/examples/simple/Makefile
+++ b/lib/wx/examples/simple/Makefile
@@ -40,7 +40,7 @@ docs:
run: opt
erl -smp -detached -pa $(TOPDIR)/ebin -s hello
-EXRELSYSDIR = $(RELSYSDIR)/examples/simple
+EXRELSYSDIR = "$(RELSYSDIR)/examples/simple"
include $(ERL_TOP)/make/otp_release_targets.mk
docs:
diff --git a/lib/wx/examples/sudoku/Makefile b/lib/wx/examples/sudoku/Makefile
index 89919ff50c..ec900f37e2 100644
--- a/lib/wx/examples/sudoku/Makefile
+++ b/lib/wx/examples/sudoku/Makefile
@@ -40,7 +40,7 @@ docs:
run: opt
erl -smp -detached -pa $(TOPDIR)/ebin -s sudoku
-EXRELSYSDIR = $(RELSYSDIR)/examples/sudoku
+EXRELSYSDIR = "$(RELSYSDIR)/examples/sudoku"
include $(ERL_TOP)/make/otp_release_targets.mk
docs:
diff --git a/lib/wx/examples/xrc/Makefile b/lib/wx/examples/xrc/Makefile
index 341fdbb2cc..9a976628a7 100644
--- a/lib/wx/examples/xrc/Makefile
+++ b/lib/wx/examples/xrc/Makefile
@@ -49,7 +49,7 @@ docs:
run: opt
erl -smp -detached -pa $(TOPDIR)/ebin -s xrc
-EXRELSYSDIR = $(RELSYSDIR)/examples/xrc
+EXRELSYSDIR = "$(RELSYSDIR)/examples/xrc"
include $(ERL_TOP)/make/otp_release_targets.mk
docs:
diff --git a/lib/wx/src/Makefile b/lib/wx/src/Makefile
index 16b425e6f0..777fb7d998 100644
--- a/lib/wx/src/Makefile
+++ b/lib/wx/src/Makefile
@@ -120,15 +120,15 @@ $(EBIN)/%.beam: $(EGEN)/%.erl $(HEADER_FILES)
# ----------------------------------------------------
include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/src/gen
- $(INSTALL_DATA) $(GEN_HRL) $(GEN_FILES) $(RELSYSDIR)/src/gen
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(EXT_HRL) $(RELSYSDIR)/include
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(HRL_FILES) $(ERL_FILES) "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src/gen"
+ $(INSTALL_DATA) $(GEN_HRL) $(GEN_FILES) "$(RELSYSDIR)/src/gen"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(EXT_HRL) "$(RELSYSDIR)/include"
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(APP_TARGET) $(APPUP_TARGET) "$(RELSYSDIR)/ebin"
# $(INSTALL_DATA) ../$(ARCHIVE) $(RELEASE_PATH)/lib
release_docs_spec:
diff --git a/lib/wx/test/Makefile b/lib/wx/test/Makefile
index ac8a4bdd60..836885a308 100644
--- a/lib/wx/test/Makefile
+++ b/lib/wx/test/Makefile
@@ -53,8 +53,8 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec:
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) wx.spec wx.cover wx_test_lib.hrl $(ErlSrc) $(ErlTargets) $(RELSYSDIR)
- $(INSTALL_SCRIPT) wxt $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) wx.spec wx.cover wx_test_lib.hrl $(ErlSrc) $(ErlTargets) "$(RELSYSDIR)"
+ $(INSTALL_SCRIPT) wxt "$(RELSYSDIR)"
release_docs_spec:
diff --git a/lib/wx/vsn.mk b/lib/wx/vsn.mk
index 3f3e9422a8..719eb0daf0 100644
--- a/lib/wx/vsn.mk
+++ b/lib/wx/vsn.mk
@@ -1 +1 @@
-WX_VSN = 0.99.1
+WX_VSN = 0.99.2
diff --git a/lib/xmerl/doc/src/Makefile b/lib/xmerl/doc/src/Makefile
index 100a2feb0a..4de06249df 100644
--- a/lib/xmerl/doc/src/Makefile
+++ b/lib/xmerl/doc/src/Makefile
@@ -161,15 +161,15 @@ info:
include $(ERL_TOP)/make/otp_release_targets.mk
release_docs_spec: docs
- $(INSTALL_DIR) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DATA) $(TOP_PDF_FILE) $(RELSYSDIR)/doc/pdf
- $(INSTALL_DIR) $(RELSYSDIR)/doc/html
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DATA) $(TOP_PDF_FILE) "$(RELSYSDIR)/doc/pdf"
+ $(INSTALL_DIR) "$(RELSYSDIR)/doc/html"
$(INSTALL_DATA) $(HTMLDIR)/* \
- $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(EXAMPLE_FILES) $(HTML_EXAMPLE_FILES) $(HTML_STYLESHEET_FILES) $(RELSYSDIR)/doc/html
- $(INSTALL_DATA) $(INFO_FILE) $(RELSYSDIR)
- $(INSTALL_DIR) $(RELEASE_PATH)/man/man3
- $(INSTALL_DATA) $(MAN3DIR)/* $(RELEASE_PATH)/man/man3
+ "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(EXAMPLE_FILES) $(HTML_EXAMPLE_FILES) $(HTML_STYLESHEET_FILES) "$(RELSYSDIR)/doc/html"
+ $(INSTALL_DATA) $(INFO_FILE) "$(RELSYSDIR)"
+ $(INSTALL_DIR) "$(RELEASE_PATH)/man/man3"
+ $(INSTALL_DATA) $(MAN3DIR)/* "$(RELEASE_PATH)/man/man3"
release_spec:
diff --git a/lib/xmerl/doc/src/notes.xml b/lib/xmerl/doc/src/notes.xml
index 8734bd8771..bd12e688d0 100644
--- a/lib/xmerl/doc/src/notes.xml
+++ b/lib/xmerl/doc/src/notes.xml
@@ -31,6 +31,64 @@
<p>This document describes the changes made to the Xmerl application.</p>
+<section><title>Xmerl 1.3.2</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p> Fix a continuation bug when a new block of bytes is
+ to be read during parsing of a default declaration. </p>
+ <p>
+ Own Id: OTP-10063 Aux Id: seq12049 </p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
+<section><title>Xmerl 1.3.1</title>
+
+ <section><title>Fixed Bugs and Malfunctions</title>
+ <list>
+ <item>
+ <p>
+ Add missing spaces in xmerl doc (Thanks to Ricardo
+ Catalinas Jim�nez)</p>
+ <p>
+ Own Id: OTP-9873</p>
+ </item>
+ <item>
+ <p> Fixed a continuation error in the sax parser and
+ added latin1 as recognized encoding (not only the
+ iso-8859 variants). </p>
+ <p>
+ Own Id: OTP-9961</p>
+ </item>
+ <item>
+ <p> Removed the unused file xmerl_xlink.hrl. Thanks to
+ Vlad Dumitrescu for informing us about it. </p>
+ <p>
+ Own Id: OTP-9965</p>
+ </item>
+ <item>
+ <p> xmerl couldn't handle comments inside a type
+ specification. </p>
+ <p>
+ Own Id: OTP-10023</p>
+ </item>
+ <item>
+ <p> Fix some small errors in the sax parser: error
+ message bug, removal of trailing blanks in DTD element
+ definitions and an documentation error of the startDTD
+ event in xmerl_sax_parser module. </p>
+ <p>
+ Own Id: OTP-10026</p>
+ </item>
+ </list>
+ </section>
+
+</section>
+
<section><title>Xmerl 1.3</title>
<section><title>Fixed Bugs and Malfunctions</title>
diff --git a/lib/xmerl/src/Makefile b/lib/xmerl/src/Makefile
index a5dbe45909..ce1aa11fba 100644
--- a/lib/xmerl/src/Makefile
+++ b/lib/xmerl/src/Makefile
@@ -214,14 +214,14 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)/ebin
- $(INSTALL_DATA) $(TARGET_FILES) $(RELSYSDIR)/ebin
- $(INSTALL_DIR) $(RELSYSDIR)/src
- $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(APP_SRC) $(APPUP_SRC) $(RELSYSDIR)/src
- $(INSTALL_DATA) xmerl_xpath_parse.yrl $(RELSYSDIR)/src
- $(INSTALL_DATA) xmerl_b64Bin.yrl $(RELSYSDIR)/src
- $(INSTALL_DIR) $(RELSYSDIR)/include
- $(INSTALL_DATA) $(HRL_FILES) $(RELSYSDIR)/include
+ $(INSTALL_DIR) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DATA) $(TARGET_FILES) "$(RELSYSDIR)/ebin"
+ $(INSTALL_DIR) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) $(ERL_FILES) $(INTERNAL_HRL_FILES) $(APP_SRC) $(APPUP_SRC) "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) xmerl_xpath_parse.yrl "$(RELSYSDIR)/src"
+ $(INSTALL_DATA) xmerl_b64Bin.yrl "$(RELSYSDIR)/src"
+ $(INSTALL_DIR) "$(RELSYSDIR)/include"
+ $(INSTALL_DATA) $(HRL_FILES) "$(RELSYSDIR)/include"
release_docs_spec:
diff --git a/lib/xmerl/src/xmerl_sax_parser_base.erlsrc b/lib/xmerl/src/xmerl_sax_parser_base.erlsrc
index df0970ef14..d38045f2a5 100644
--- a/lib/xmerl/src/xmerl_sax_parser_base.erlsrc
+++ b/lib/xmerl/src/xmerl_sax_parser_base.erlsrc
@@ -155,16 +155,16 @@ parse_xml_decl(?BYTE_ORDER_MARK_2, State) ->
cf(?BYTE_ORDER_MARK_2, State, fun parse_xml_decl/2);
parse_xml_decl(?BYTE_ORDER_MARK_REST(Rest), State) ->
cf(Rest, State, fun parse_xml_decl/2);
-parse_xml_decl(?STRING("<"), State) ->
- cf(?STRING("<"), State, fun parse_xml_decl/2);
-parse_xml_decl(?STRING("<?"), State) ->
- cf(?STRING("<?"), State, fun parse_xml_decl/2);
-parse_xml_decl(?STRING("<?x"), State) ->
- cf(?STRING("<?x"), State, fun parse_xml_decl/2);
-parse_xml_decl(?STRING("<?xm"), State) ->
- cf(?STRING("<?xm"), State, fun parse_xml_decl/2);
-parse_xml_decl(?STRING("<?xml"), State) ->
- cf(?STRING("<?xml"), State, fun parse_xml_decl/2);
+parse_xml_decl(?STRING("<") = Bytes, State) ->
+ cf(Bytes, State, fun parse_xml_decl/2);
+parse_xml_decl(?STRING("<?") = Bytes, State) ->
+ cf(Bytes, State, fun parse_xml_decl/2);
+parse_xml_decl(?STRING("<?x") = Bytes, State) ->
+ cf(Bytes, State, fun parse_xml_decl/2);
+parse_xml_decl(?STRING("<?xm") = Bytes, State) ->
+ cf(Bytes, State, fun parse_xml_decl/2);
+parse_xml_decl(?STRING("<?xml") = Bytes, State) ->
+ cf(Bytes, State, fun parse_xml_decl/2);
parse_xml_decl(?STRING_REST("<?xml", Rest1), State) ->
parse_xml_decl_1(Rest1, State);
parse_xml_decl(Bytes, #xmerl_sax_parser_state{encoding=Enc} = State) when is_binary(Bytes) ->
@@ -204,8 +204,8 @@ parse_xml_decl_1(Bytes, State) ->
%%----------------------------------------------------------------------
parse_prolog(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_prolog/2);
-parse_prolog(?STRING("<"), State) ->
- cf(?STRING("<"), State, fun parse_prolog/2);
+parse_prolog(?STRING("<") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog/2);
parse_prolog(?STRING_REST("<?", Rest), State) ->
{Rest1, State1} = parse_pi(Rest, State),
parse_prolog(Rest1, State1);
@@ -223,18 +223,18 @@ parse_prolog(Bytes, State) ->
parse_prolog_1(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("D"), State) ->
- cf(?STRING("D"), State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("DO"), State) ->
- cf(?STRING("DO"), State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("DOC"), State) ->
- cf(?STRING("DOC"), State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("DOCT"), State) ->
- cf(?STRING("DOCT"), State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("DOCTY"), State) ->
- cf(?STRING("DOCTY"), State, fun parse_prolog_1/2);
-parse_prolog_1(?STRING("DOCTYP"), State) ->
- cf(?STRING("DOCTYP"), State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("D") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("DO") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("DOC") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("DOCT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("DOCTY") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
+parse_prolog_1(?STRING("DOCTYP") = Bytes, State) ->
+ cf(Bytes, State, fun parse_prolog_1/2);
parse_prolog_1(?STRING_REST("DOCTYPE", Rest), State) ->
{Rest1, State1} = parse_doctype(Rest, State),
State2 = event_callback(endDTD, State1),
@@ -512,10 +512,10 @@ parse_ns_name(Bytes, State, Prefix, Name) ->
%%----------------------------------------------------------------------
parse_pi_data(?STRING_EMPTY, State, Acc) ->
cf(?STRING_EMPTY, State, Acc, fun parse_pi_data/3);
-parse_pi_data(?STRING("?"), State, Acc) ->
- cf(?STRING("?"), State, Acc, fun parse_pi_data/3);
-parse_pi_data(?STRING("\r"), State, Acc) ->
- cf(?STRING("\r"), State, Acc, fun parse_pi_data/3);
+parse_pi_data(?STRING("?") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_pi_data/3);
+parse_pi_data(?STRING("\r") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_pi_data/3);
parse_pi_data(?STRING_REST("?>", Rest), State, Acc) ->
{lists:reverse(Acc), Rest, State};
parse_pi_data(?STRING_REST("\n", Rest), #xmerl_sax_parser_state{line_no=N} = State, Acc) ->
@@ -544,23 +544,23 @@ parse_pi_data(Bytes, State, Acc) ->
%%----------------------------------------------------------------------
parse_cdata(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_cdata/2);
-parse_cdata(?STRING("["), State) ->
- cf(?STRING("["), State, fun parse_cdata/2);
-parse_cdata(?STRING("[C"), State) ->
- cf(?STRING("[C"), State, fun parse_cdata/2);
-parse_cdata(?STRING("[CD"), State) ->
- cf(?STRING("[CD"), State, fun parse_cdata/2);
-parse_cdata(?STRING("[CDA"), State) ->
- cf(?STRING("[CDA"), State, fun parse_cdata/2);
-parse_cdata(?STRING("[CDAT"), State) ->
- cf(?STRING("[CDAT"), State, fun parse_cdata/2);
-parse_cdata(?STRING("[CDATA"), State) ->
- cf(?STRING("[CDATA"), State, fun parse_cdata/2);
-parse_cdata(?STRING_REST("[CDATA[", Rest), State) ->
- State1 = event_callback(startCDATA, State),
+parse_cdata(?STRING("[") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING("[C") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING("[CD") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING("[CDA") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING("[CDAT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING("[CDATA") = Bytes, State) ->
+ cf(Bytes, State, fun parse_cdata/2);
+parse_cdata(?STRING_REST("[CDATA[", Rest), State) ->
+ State1 = event_callback(startCDATA, State),
parse_cdata(Rest, State1, []);
-parse_cdata(Bytes, State) ->
- unicode_incomplete_check([Bytes, State, fun parse_cdata/2],
+parse_cdata(Bytes, State) ->
+ unicode_incomplete_check([Bytes, State, fun parse_cdata/2],
"expecting comment or CDATA").
@@ -574,12 +574,12 @@ parse_cdata(Bytes, State) ->
%%----------------------------------------------------------------------
parse_cdata(?STRING_EMPTY, State, Acc) ->
cf(?STRING_EMPTY, State, Acc, fun parse_cdata/3);
-parse_cdata(?STRING("\r"), State, Acc) ->
- cf(?STRING("\r"), State, Acc, fun parse_cdata/3);
-parse_cdata(?STRING("]"), State, Acc) ->
- cf(?STRING("]"), State, Acc, fun parse_cdata/3);
-parse_cdata(?STRING("]]"), State, Acc) ->
- cf(?STRING("]]"), State, Acc, fun parse_cdata/3);
+parse_cdata(?STRING("\r") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_cdata/3);
+parse_cdata(?STRING("]") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_cdata/3);
+parse_cdata(?STRING("]]") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_cdata/3);
parse_cdata(?STRING_REST("]]>", Rest), State, Acc) ->
State1 = event_callback({characters, lists:reverse(Acc)}, State),
State2 = event_callback(endCDATA, State1),
@@ -610,12 +610,12 @@ parse_cdata(Bytes, State, Acc) ->
%%----------------------------------------------------------------------
parse_comment(?STRING_EMPTY, State, Acc) ->
cf(?STRING_EMPTY, State, Acc, fun parse_comment/3);
-parse_comment(?STRING("\r"), State, Acc) ->
- cf(?STRING("\r"), State, Acc, fun parse_comment/3);
-parse_comment(?STRING("-"), State, Acc) ->
- cf(?STRING("-"), State, Acc, fun parse_comment/3);
-parse_comment(?STRING("--"), State, Acc) ->
- cf(?STRING("--"), State, Acc, fun parse_comment/3);
+parse_comment(?STRING("\r") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_comment/3);
+parse_comment(?STRING("-") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_comment/3);
+parse_comment(?STRING("--") = Bytes, State, Acc) ->
+ cf(Bytes, State, Acc, fun parse_comment/3);
parse_comment(?STRING_REST("-->", Rest), State, Acc) ->
State1 = event_callback({comment, lists:reverse(Acc)}, State),
{Rest, State1};
@@ -713,8 +713,8 @@ parse_stag(Bytes, State) ->
%%----------------------------------------------------------------------
parse_attributes(?STRING_EMPTY, State, CurrentTag) ->
cf(?STRING_EMPTY, State, CurrentTag, fun parse_attributes/3);
-parse_attributes(?STRING("/"), State, CurrentTag) ->
- cf(?STRING("/"), State, CurrentTag, fun parse_attributes/3);
+parse_attributes(?STRING("/") = Bytes, State, CurrentTag) ->
+ cf(Bytes, State, CurrentTag, fun parse_attributes/3);
parse_attributes(?STRING_REST("/>", Rest), State, {Tag, AttList, NewNsList}) ->
CompleteNsList = NewNsList ++ State#xmerl_sax_parser_state.ns,
{Uri, LocalName, QName, Attributes} = fix_ns(Tag, AttList, CompleteNsList),
@@ -911,20 +911,20 @@ parse_att_value(?STRING_EMPTY, State, undefined, Acc) ->
{Acc, [], State}; %% stop clause when parsing references
parse_att_value(?STRING_EMPTY, State, Stop, Acc) ->
cf(?STRING_EMPTY, State, Stop, Acc, fun parse_att_value/4);
-parse_att_value(?STRING("\r"), State, Stop, Acc) ->
- cf(?STRING("\r"), State, Stop, Acc, fun parse_att_value/4);
+parse_att_value(?STRING("\r") = Bytes, State, Stop, Acc) ->
+ cf(Bytes, State, Stop, Acc, fun parse_att_value/4);
parse_att_value(?STRING_REST("\n", Rest), #xmerl_sax_parser_state{line_no=N} = State, Stop, Acc) ->
parse_att_value(Rest,
- State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
+ State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
parse_att_value(?STRING_REST("\r\n", Rest), #xmerl_sax_parser_state{line_no=N} = State, Stop, Acc) ->
parse_att_value(Rest,
- State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
+ State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
parse_att_value(?STRING_REST("\r", Rest), #xmerl_sax_parser_state{line_no=N} = State, Stop, Acc) ->
parse_att_value(Rest,
- State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
+ State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
parse_att_value(?STRING_REST("\t", Rest), #xmerl_sax_parser_state{line_no=N} = State, Stop, Acc) ->
parse_att_value(Rest,
- State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
+ State#xmerl_sax_parser_state{line_no=N+1}, Stop, [?space |Acc]);
parse_att_value(?STRING_REST("&", Rest), State, Stop, Acc) ->
{Ref, Rest1, State1} = parse_reference(Rest, State, true),
case Ref of
@@ -1046,17 +1046,17 @@ parse_content(?STRING_EMPTY, State, Acc, IgnorableWS) ->
Other ->
throw(Other)
end;
-parse_content(?STRING("\r"), State, Acc, IgnorableWS) ->
- cf(?STRING("\r"), State, Acc, IgnorableWS, fun parse_content/4);
-parse_content(?STRING("<"), State, Acc, IgnorableWS) ->
- cf(?STRING("<"), State, Acc, IgnorableWS, fun parse_content/4);
+parse_content(?STRING("\r") = Bytes, State, Acc, IgnorableWS) ->
+ cf(Bytes, State, Acc, IgnorableWS, fun parse_content/4);
+parse_content(?STRING("<") = Bytes, State, Acc, IgnorableWS) ->
+ cf(Bytes, State, Acc, IgnorableWS, fun parse_content/4);
parse_content(?STRING_REST("</", Rest), State, Acc, IgnorableWS) ->
State1 = send_character_event(length(Acc), IgnorableWS, lists:reverse(Acc), State),
parse_etag(Rest, State1);
-parse_content(?STRING("<!"), State, _Acc, IgnorableWS) ->
- cf(?STRING("<!"), State, [], IgnorableWS, fun parse_content/4);
-parse_content(?STRING("<!-"), State, _Acc, IgnorableWS) ->
- cf(?STRING("<!-"), State, [], IgnorableWS, fun parse_content/4);
+parse_content(?STRING("<!") = Bytes, State, _Acc, IgnorableWS) ->
+ cf(Bytes, State, [], IgnorableWS, fun parse_content/4);
+parse_content(?STRING("<!-") = Bytes, State, _Acc, IgnorableWS) ->
+ cf(Bytes, State, [], IgnorableWS, fun parse_content/4);
parse_content(?STRING_REST("<!--", Rest), State, Acc, IgnorableWS) ->
State1 = send_character_event(length(Acc), IgnorableWS, lists:reverse(Acc), State),
{Rest1, State2} = parse_comment(Rest, State1, []),
@@ -1227,8 +1227,8 @@ whitespace(Bytes, #xmerl_sax_parser_state{encoding=Enc} = State, Acc) when is_bi
%%----------------------------------------------------------------------
parse_reference(?STRING_EMPTY, State, HaveToExist) ->
cf(?STRING_EMPTY, State, HaveToExist, fun parse_reference/3);
-parse_reference(?STRING("#"), State, HaveToExist) ->
- cf(?STRING("#"), State, HaveToExist, fun parse_reference/3);
+parse_reference(?STRING("#") = Bytes, State, HaveToExist) ->
+ cf(Bytes, State, HaveToExist, fun parse_reference/3);
parse_reference(?STRING_REST("#x", Rest), State, _HaveToExist) ->
{CharValue, RefString, Rest1, State1} = parse_hex(Rest, State, []),
if
@@ -1702,16 +1702,16 @@ parse_external_entity_1(?BYTE_ORDER_MARK_2, State) ->
cf(?BYTE_ORDER_MARK_2, State, fun parse_external_entity_1/2);
parse_external_entity_1(?BYTE_ORDER_MARK_REST(Rest), State) ->
parse_external_entity_1(Rest, State);
-parse_external_entity_1(?STRING("<"), State) ->
- cf(?STRING("<"), State, fun parse_external_entity_1/2);
-parse_external_entity_1(?STRING("<?"), State) ->
- cf(?STRING("<?"), State, fun parse_external_entity_1/2);
-parse_external_entity_1(?STRING("<?x"), State) ->
- cf(?STRING("<?x"), State, fun parse_external_entity_1/2);
-parse_external_entity_1(?STRING("<?xm"), State) ->
- cf(?STRING("<?xm"), State, fun parse_external_entity_1/2);
-parse_external_entity_1(?STRING("<?xml"), State) ->
- cf(?STRING("<?xml"), State, fun parse_external_entity_1/2);
+parse_external_entity_1(?STRING("<") = Bytes, State) ->
+ cf(Bytes, State, fun parse_external_entity_1/2);
+parse_external_entity_1(?STRING("<?") = Bytes, State) ->
+ cf(Bytes, State, fun parse_external_entity_1/2);
+parse_external_entity_1(?STRING("<?x") = Bytes, State) ->
+ cf(Bytes, State, fun parse_external_entity_1/2);
+parse_external_entity_1(?STRING("<?xm") = Bytes, State) ->
+ cf(Bytes, State, fun parse_external_entity_1/2);
+parse_external_entity_1(?STRING("<?xml") = Bytes, State) ->
+ cf(Bytes, State, fun parse_external_entity_1/2);
parse_external_entity_1(?STRING_REST("<?xml", Rest) = Bytes,
#xmerl_sax_parser_state{file_type=Type} = State) ->
{Rest1, State1} =
@@ -1781,29 +1781,29 @@ is_next_char_whitespace(Bytes, State) ->
%%----------------------------------------------------------------------
parse_external_id(?STRING_EMPTY, State, OptionalSystemId) ->
cf(?STRING_EMPTY, State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("S"), State,OptionalSystemId) ->
- cf(?STRING("S"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("SY"), State, OptionalSystemId) ->
- cf(?STRING("SY"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("SYS"), State, OptionalSystemId) ->
- cf(?STRING("SYS"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("SYST"), State, OptionalSystemId) ->
- cf(?STRING("SYST"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("SYSTE"), State, OptionalSystemId) ->
- cf(?STRING("SYSTE"), State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("S") = Bytes, State,OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("SY") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("SYS") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("SYST") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("SYSTE") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
parse_external_id(?STRING_REST("SYSTEM", Rest), State, _) ->
{SysId, Rest1, State1} = parse_system_id(Rest, State, false),
{"", SysId, Rest1, State1};
-parse_external_id(?STRING("P"), State, OptionalSystemId) ->
- cf(?STRING("P"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("PU"), State, OptionalSystemId) ->
- cf(?STRING("PU"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("PUB"), State, OptionalSystemId) ->
- cf(?STRING("PUB"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("PUBL"), State, OptionalSystemId) ->
- cf(?STRING("PUBL"), State, OptionalSystemId, fun parse_external_id/3);
-parse_external_id(?STRING("PUBLI"), State, OptionalSystemId) ->
- cf(?STRING("PUBLI"), State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("P") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("PU") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("PUB") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("PUBL") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
+parse_external_id(?STRING("PUBLI") = Bytes, State, OptionalSystemId) ->
+ cf(Bytes, State, OptionalSystemId, fun parse_external_id/3);
parse_external_id(?STRING_REST("PUBLIC", Rest), State, OptionalSystemId) ->
parse_public_id(Rest, State, OptionalSystemId);
parse_external_id(Bytes, State, OptionalSystemId) ->
@@ -1923,70 +1923,70 @@ parse_doctype_decl(Bytes, State) ->
parse_doctype_decl_1(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("E"), State) ->
- cf(?STRING("E"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("EL"), State) ->
- cf(?STRING("EL"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ELE"), State) ->
- cf(?STRING("ELE"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ELEM"), State) ->
- cf(?STRING("ELEM"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ELEME"), State) ->
- cf(?STRING("ELEME"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ELEMEN"), State) ->
- cf(?STRING("ELEMEN"), State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("E") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("EL") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ELE") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ELEM") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ELEME") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ELEMEN") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
parse_doctype_decl_1(?STRING_REST("ELEMENT", Rest), State) ->
{Rest1, State1} = parse_element_decl(Rest, State),
parse_doctype_decl(Rest1, State1);
-parse_doctype_decl_1(?STRING("A"), State) ->
- cf(?STRING("A"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("AT"), State) ->
- cf(?STRING("AT"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ATT"), State) ->
- cf(?STRING("ATT"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ATTL"), State) ->
- cf(?STRING("ATTL"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ATTLI"), State) ->
- cf(?STRING("ATTLI"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ATTLIS"), State) ->
- cf(?STRING("ATTLIS"), State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("A") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("AT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ATT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ATTL") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ATTLI") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ATTLIS") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
parse_doctype_decl_1(?STRING_REST("ATTLIST", Rest), State) ->
{Rest1, State1} = parse_att_list_decl(Rest, State),
parse_doctype_decl(Rest1, State1);
%% E clause not needed here because already taken care of above.
-parse_doctype_decl_1(?STRING("EN"), State) ->
- cf(?STRING("EN"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ENT"), State) ->
- cf(?STRING("ENT"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ENTI"), State) ->
- cf(?STRING("ENTI"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("ENTIT"), State) ->
- cf(?STRING("ENTIT"), State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("EN") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ENT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ENTI") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("ENTIT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
parse_doctype_decl_1(?STRING_REST("ENTITY", Rest), State) ->
{Rest1, State1} = parse_entity_decl(Rest, State),
parse_doctype_decl(Rest1, State1);
-parse_doctype_decl_1(?STRING("N"), State) ->
- cf(?STRING("N"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NO"), State) ->
- cf(?STRING("NO"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NOT"), State) ->
- cf(?STRING("NOT"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NOTA"), State) ->
- cf(?STRING("NOTA"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NOTAT"), State) ->
- cf(?STRING("NOTAT"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NOTATI"), State) ->
- cf(?STRING("NOTATI"), State, fun parse_doctype_decl_1/2);
-parse_doctype_decl_1(?STRING("NOTATIO"), State) ->
- cf(?STRING("NOTATIO"), State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("N") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NO") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NOT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NOTA") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NOTAT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NOTATI") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("NOTATIO") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
parse_doctype_decl_1(?STRING_REST("NOTATION", Rest), State) ->
{Rest1, State1} = parse_notation_decl(Rest, State),
parse_doctype_decl(Rest1, State1);
-parse_doctype_decl_1(?STRING("-"), State) ->
- cf(?STRING("-"), State, fun parse_doctype_decl_1/2);
+parse_doctype_decl_1(?STRING("-") = Bytes, State) ->
+ cf(Bytes, State, fun parse_doctype_decl_1/2);
parse_doctype_decl_1(?STRING_REST("--", Rest), State) ->
{Rest1, State1} = parse_comment(Rest, State, []),
parse_doctype_decl(Rest1, State1);
@@ -2264,52 +2264,52 @@ parse_default_decl(Bytes, State) ->
%%----------------------------------------------------------------------
parse_default_decl_1(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_default_decl_1/2);
-parse_default_decl_1(?STRING_REST("#", Rest), State) ->
- case Rest of
- ?STRING("R") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("RE") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("REQ") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("REQU") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("REQUI") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("REQUIR") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("REQUIRE") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING_REST("REQUIRED", Rest1) ->
+parse_default_decl_1(?STRING_REST("#", _Rest) = Bytes, State) ->
+ case Bytes of
+ ?STRING("#R") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#RE") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#REQ") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#REQU") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#REQUI") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#REQUIR") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#REQUIRE") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING_REST("#REQUIRED", Rest1) ->
{"#REQUIRED", undefined, Rest1, State};
- ?STRING("I") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("IM") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("IMP") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("IMPL") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("IMPLI") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("IMPLIE") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING_REST("IMPLIED", Rest1) ->
+ ?STRING("#I") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#IM") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#IMP") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#IMPL") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#IMPLI") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#IMPLIE") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING_REST("#IMPLIED", Rest1) ->
{"#IMPLIED", undefined, Rest1, State};
- ?STRING("F") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("FI") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("FIX") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING("FIXE") ->
- cf(Rest, State, fun parse_default_decl_1/2);
- ?STRING_REST("FIXED", Rest1) ->
+ ?STRING("#F") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#FI") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#FIX") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING("#FIXE") ->
+ cf(Bytes, State, fun parse_default_decl_1/2);
+ ?STRING_REST("#FIXED", Rest1) ->
parse_fixed(Rest1, State);
_ ->
- ?fatal_error(State, "REQUIRED, IMPLIED or FIXED expected")
+ ?fatal_error(State, "REQUIRED, IMPLIED or FIXED expected after #")
end;
parse_default_decl_1(?STRING_UNBOUND_REST(C, Rest), State) when C == $'; C == $" ->
{DefaultValue, Rest1, State1} = parse_att_value(Rest, State, C, []),
@@ -2560,14 +2560,14 @@ parse_ndata_decl(?STRING_EMPTY, State) ->
cf(?STRING_EMPTY, State, fun parse_ndata_decl/2);
parse_ndata_decl(?STRING_REST(">", Rest), State) ->
{undefined, Rest, State};
-parse_ndata_decl(?STRING("N") = Rest, State) ->
- cf(Rest, State, fun parse_ndata_decl/2);
-parse_ndata_decl(?STRING("ND") = Rest, State) ->
- cf(Rest, State, fun parse_ndata_decl/2);
-parse_ndata_decl(?STRING("NDA") = Rest, State) ->
- cf(Rest, State, fun parse_ndata_decl/2);
-parse_ndata_decl(?STRING("NDAT") = Rest, State) ->
- cf(Rest, State, fun parse_ndata_decl/2);
+parse_ndata_decl(?STRING("N") = Bytes, State) ->
+ cf(Bytes, State, fun parse_ndata_decl/2);
+parse_ndata_decl(?STRING("ND") = Bytes, State) ->
+ cf(Bytes, State, fun parse_ndata_decl/2);
+parse_ndata_decl(?STRING("NDA") = Bytes, State) ->
+ cf(Bytes, State, fun parse_ndata_decl/2);
+parse_ndata_decl(?STRING("NDAT") = Bytes, State) ->
+ cf(Bytes, State, fun parse_ndata_decl/2);
parse_ndata_decl(?STRING_REST("NDATA", Rest), State) ->
parse_ndata_decl_1(Rest, State);
parse_ndata_decl(Bytes, State) ->
diff --git a/lib/xmerl/test/Makefile b/lib/xmerl/test/Makefile
index 5a2a585841..1fdbb7ca0d 100644
--- a/lib/xmerl/test/Makefile
+++ b/lib/xmerl/test/Makefile
@@ -113,15 +113,15 @@ include $(ERL_TOP)/make/otp_release_targets.mk
release_spec: opt
release_tests_spec: opt
- $(INSTALL_DIR) $(RELSYSDIR)
- $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) $(SUITE_FILES) $(RELSYSDIR)
- $(INSTALL_DATA) xmerl.spec xmerl.cover $(RELSYSDIR)
- cp $(XML_FILES) $(RELSYSDIR)
- @tar cfh - xmerl_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- @tar cfh - xmerl_std_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- @tar cfh - xmerl_xsd_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- @tar cfh - xmerl_xsd_MS2002-01-16_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- @tar cfh - xmerl_xsd_NIST2002-01-16_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- @tar cfh - xmerl_xsd_Sun2002-01-16_SUITE_data | (cd $(RELSYSDIR); tar xf -)
- chmod -R u+w $(RELSYSDIR)
+ $(INSTALL_DIR) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(ERL_FILES) $(HRL_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) $(SUITE_FILES) "$(RELSYSDIR)"
+ $(INSTALL_DATA) xmerl.spec xmerl.cover "$(RELSYSDIR)"
+ cp $(XML_FILES) "$(RELSYSDIR)"
+ @tar cfh - xmerl_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ @tar cfh - xmerl_std_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ @tar cfh - xmerl_xsd_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ @tar cfh - xmerl_xsd_MS2002-01-16_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ @tar cfh - xmerl_xsd_NIST2002-01-16_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ @tar cfh - xmerl_xsd_Sun2002-01-16_SUITE_data | (cd "$(RELSYSDIR)"; tar xf -)
+ chmod -R u+w "$(RELSYSDIR)"
diff --git a/lib/xmerl/vsn.mk b/lib/xmerl/vsn.mk
index de47e3418b..599bc0b9d3 100644
--- a/lib/xmerl/vsn.mk
+++ b/lib/xmerl/vsn.mk
@@ -1 +1 @@
-XMERL_VSN = 1.3
+XMERL_VSN = 1.3.2