diff options
Diffstat (limited to 'lib/tools')
55 files changed, 3941 insertions, 4189 deletions
diff --git a/lib/tools/Makefile b/lib/tools/Makefile index fef33743c0..e17e9cfd1e 100644 --- a/lib/tools/Makefile +++ b/lib/tools/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 1996-2009. All Rights Reserved. +# Copyright Ericsson AB 1996-2016. All Rights Reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/lib/tools/c_src/Makefile.in b/lib/tools/c_src/Makefile.in index e8bce149b1..cfe91917f8 100644 --- a/lib/tools/c_src/Makefile.in +++ b/lib/tools/c_src/Makefile.in @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 2009-2012. All Rights Reserved. +# Copyright Ericsson AB 2009-2016. All Rights Reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/lib/tools/c_src/erl_memory.c b/lib/tools/c_src/erl_memory.c index d3a96884db..13a3fccc6d 100644 --- a/lib/tools/c_src/erl_memory.c +++ b/lib/tools/c_src/erl_memory.c @@ -1,7 +1,7 @@ /* * %CopyrightBegin% * - * Copyright Ericsson AB 2003-2013. All Rights Reserved. + * Copyright Ericsson AB 2003-2016. All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. diff --git a/lib/tools/doc/src/Makefile b/lib/tools/doc/src/Makefile index c44c9ef4df..d9c3b0ad2a 100644 --- a/lib/tools/doc/src/Makefile +++ b/lib/tools/doc/src/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 1997-2012. All Rights Reserved. +# Copyright Ericsson AB 1997-2016. All Rights Reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/lib/tools/doc/src/book.xml b/lib/tools/doc/src/book.xml index 03afa1fc37..38d0408156 100644 --- a/lib/tools/doc/src/book.xml +++ b/lib/tools/doc/src/book.xml @@ -4,7 +4,7 @@ <book xmlns:xi="http://www.w3.org/2001/XInclude"> <header titlestyle="normal"> <copyright> - <year>1997</year><year>2013</year> + <year>1997</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/cover_chapter.xml b/lib/tools/doc/src/cover_chapter.xml index c3f1570477..3847adbe59 100644 --- a/lib/tools/doc/src/cover_chapter.xml +++ b/lib/tools/doc/src/cover_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2001</year><year>2013</year> + <year>2001</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/cprof.xml b/lib/tools/doc/src/cprof.xml index d3be276d28..df0acbe617 100644 --- a/lib/tools/doc/src/cprof.xml +++ b/lib/tools/doc/src/cprof.xml @@ -5,7 +5,7 @@ <header> <copyright> <year>2002</year> - <year>2013</year> + <year>2016</year> <holder>Ericsson AB, All Rights Reserved</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/cprof_chapter.xml b/lib/tools/doc/src/cprof_chapter.xml index 0e83dbbfb5..ba1e7432fd 100644 --- a/lib/tools/doc/src/cprof_chapter.xml +++ b/lib/tools/doc/src/cprof_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2002</year><year>2013</year> + <year>2002</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/eprof.xml b/lib/tools/doc/src/eprof.xml index 8e37d49c99..f098b7d39e 100644 --- a/lib/tools/doc/src/eprof.xml +++ b/lib/tools/doc/src/eprof.xml @@ -4,7 +4,7 @@ <erlref> <header> <copyright> - <year>1996</year><year>2013</year> + <year>1996</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/erlang_mode.xml b/lib/tools/doc/src/erlang_mode.xml index 4ecb8feadd..00cf5196b4 100644 --- a/lib/tools/doc/src/erlang_mode.xml +++ b/lib/tools/doc/src/erlang_mode.xml @@ -4,7 +4,7 @@ <erlref> <header> <copyright> - <year>2003</year><year>2013</year> + <year>2003</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> @@ -252,6 +252,7 @@ behavior</item> <item>gen_event - skeleton for the OTP gen_event behavior</item> <item>gen_fsm - skeleton for the OTP gen_fsm behavior</item> + <item>gen_statem - skeleton for the OTP gen_statem behavior</item> <item>Library module - skeleton for a module that does not implement a process.</item> <item>Corba callback - skeleton for a Corba callback module.</item> diff --git a/lib/tools/doc/src/erlang_mode_chapter.xml b/lib/tools/doc/src/erlang_mode_chapter.xml index e07e7a8176..b4e30d883b 100644 --- a/lib/tools/doc/src/erlang_mode_chapter.xml +++ b/lib/tools/doc/src/erlang_mode_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2003</year><year>2013</year> + <year>2003</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/fprof.xml b/lib/tools/doc/src/fprof.xml index 2dfc77fdfc..4c9e48045e 100644 --- a/lib/tools/doc/src/fprof.xml +++ b/lib/tools/doc/src/fprof.xml @@ -4,7 +4,7 @@ <erlref> <header> <copyright> - <year>2001</year><year>2013</year> + <year>2001</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/fprof_chapter.xml b/lib/tools/doc/src/fprof_chapter.xml index ecd8f385a5..5a2a5ad47c 100644 --- a/lib/tools/doc/src/fprof_chapter.xml +++ b/lib/tools/doc/src/fprof_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2001</year><year>2013</year> + <year>2001</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/instrument.xml b/lib/tools/doc/src/instrument.xml index 76583cd03b..bb6f9b6100 100644 --- a/lib/tools/doc/src/instrument.xml +++ b/lib/tools/doc/src/instrument.xml @@ -4,7 +4,7 @@ <erlref> <header> <copyright> - <year>1998</year><year>2013</year> + <year>1998</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/lcnt.xml b/lib/tools/doc/src/lcnt.xml index c381488f85..9c8ce148e9 100644 --- a/lib/tools/doc/src/lcnt.xml +++ b/lib/tools/doc/src/lcnt.xml @@ -5,7 +5,7 @@ <header> <copyright> <year>2009</year> - <year>2013</year> + <year>2016</year> <holder>Ericsson AB, All Rights Reserved</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/lcnt_chapter.xml b/lib/tools/doc/src/lcnt_chapter.xml index 060559c954..6cfdb5cf1b 100644 --- a/lib/tools/doc/src/lcnt_chapter.xml +++ b/lib/tools/doc/src/lcnt_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2009</year><year>2013</year> + <year>2009</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/make.xml b/lib/tools/doc/src/make.xml index 5c2e5e5d62..fddf5ebd7b 100644 --- a/lib/tools/doc/src/make.xml +++ b/lib/tools/doc/src/make.xml @@ -5,7 +5,7 @@ <header> <copyright> <year>1996</year> - <year>2013</year> + <year>2016</year> <holder>Ericsson AB, All Rights Reserved</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/notes.xml b/lib/tools/doc/src/notes.xml index c62b0607ee..3a6ac37eef 100644 --- a/lib/tools/doc/src/notes.xml +++ b/lib/tools/doc/src/notes.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2004</year><year>2013</year> + <year>2004</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/notes_history.xml b/lib/tools/doc/src/notes_history.xml index d19aac4d4e..d955cbde69 100644 --- a/lib/tools/doc/src/notes_history.xml +++ b/lib/tools/doc/src/notes_history.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2006</year><year>2013</year> + <year>2006</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/part.xml b/lib/tools/doc/src/part.xml index b96586041a..796047fe8d 100644 --- a/lib/tools/doc/src/part.xml +++ b/lib/tools/doc/src/part.xml @@ -4,7 +4,7 @@ <part xmlns:xi="http://www.w3.org/2001/XInclude"> <header> <copyright> - <year>1996</year><year>2013</year> + <year>1996</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/part_notes.xml b/lib/tools/doc/src/part_notes.xml index c990e973a2..c4c6fa4d7d 100644 --- a/lib/tools/doc/src/part_notes.xml +++ b/lib/tools/doc/src/part_notes.xml @@ -4,7 +4,7 @@ <part xmlns:xi="http://www.w3.org/2001/XInclude"> <header> <copyright> - <year>2004</year><year>2013</year> + <year>2004</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/part_notes_history.xml b/lib/tools/doc/src/part_notes_history.xml index dd9c27e872..a34e35fc56 100644 --- a/lib/tools/doc/src/part_notes_history.xml +++ b/lib/tools/doc/src/part_notes_history.xml @@ -5,7 +5,7 @@ <header> <copyright> <year>2006</year> - <year>2013</year> + <year>2016</year> <holder>Ericsson AB, All Rights Reserved</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/ref_man.xml b/lib/tools/doc/src/ref_man.xml index 2d9ca7660a..d2131e7a93 100644 --- a/lib/tools/doc/src/ref_man.xml +++ b/lib/tools/doc/src/ref_man.xml @@ -4,7 +4,7 @@ <application xmlns:xi="http://www.w3.org/2001/XInclude"> <header> <copyright> - <year>1996</year><year>2013</year> + <year>1996</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/tags.xml b/lib/tools/doc/src/tags.xml index b089f0674b..ea0ae5cc4d 100644 --- a/lib/tools/doc/src/tags.xml +++ b/lib/tools/doc/src/tags.xml @@ -5,7 +5,7 @@ <header> <copyright> <year>1998</year> - <year>2013</year> + <year>2016</year> <holder>Ericsson AB, All Rights Reserved</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/xref.xml b/lib/tools/doc/src/xref.xml index ebf9139f06..8c49f3a206 100644 --- a/lib/tools/doc/src/xref.xml +++ b/lib/tools/doc/src/xref.xml @@ -4,7 +4,7 @@ <erlref> <header> <copyright> - <year>2000</year><year>2013</year> + <year>2000</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/doc/src/xref_chapter.xml b/lib/tools/doc/src/xref_chapter.xml index e7186b9209..8b14e03064 100644 --- a/lib/tools/doc/src/xref_chapter.xml +++ b/lib/tools/doc/src/xref_chapter.xml @@ -4,7 +4,7 @@ <chapter> <header> <copyright> - <year>2000</year><year>2013</year> + <year>2000</year><year>2016</year> <holder>Ericsson AB. All Rights Reserved.</holder> </copyright> <legalnotice> diff --git a/lib/tools/emacs/erlang-eunit.el b/lib/tools/emacs/erlang-eunit.el index a3c29c520c..3b85e6680a 100644 --- a/lib/tools/emacs/erlang-eunit.el +++ b/lib/tools/emacs/erlang-eunit.el @@ -1,7 +1,7 @@ ;; ;; %CopyrightBegin% ;; -;; Copyright Ericsson AB 2009-2010. All Rights Reserved. +;; Copyright Ericsson AB 2009-2016. All Rights Reserved. ;; ;; Licensed under the Apache License, Version 2.0 (the "License"); ;; you may not use this file except in compliance with the License. diff --git a/lib/tools/emacs/erlang-skels-old.el b/lib/tools/emacs/erlang-skels-old.el index d0b2bfd97f..4087bc3013 100644 --- a/lib/tools/emacs/erlang-skels-old.el +++ b/lib/tools/emacs/erlang-skels-old.el @@ -1,7 +1,7 @@ ;; ;; %CopyrightBegin% ;; -;; Copyright Ericsson AB 2010. All Rights Reserved. +;; Copyright Ericsson AB 2010-2016. All Rights Reserved. ;; ;; Licensed under the Apache License, Version 2.0 (the "License"); ;; you may not use this file except in compliance with the License. diff --git a/lib/tools/emacs/erlang-skels.el b/lib/tools/emacs/erlang-skels.el index ac37ff2ee5..ce26c83295 100644 --- a/lib/tools/emacs/erlang-skels.el +++ b/lib/tools/emacs/erlang-skels.el @@ -1,7 +1,7 @@ ;; ;; %CopyrightBegin% ;; -;; Copyright Ericsson AB 2010-2014. All Rights Reserved. +;; Copyright Ericsson AB 2010-2016. All Rights Reserved. ;; ;; Licensed under the Apache License, Version 2.0 (the "License"); ;; you may not use this file except in compliance with the License. @@ -56,6 +56,8 @@ erlang-skel-gen-event erlang-skel-header) ("gen_fsm" "gen-fsm" erlang-skel-gen-fsm erlang-skel-header) + ("gen_statem" "gen-statem" + erlang-skel-gen-statem erlang-skel-header) ("wx_object" "wx-object" erlang-skel-wx-object erlang-skel-header) ("Library module" "gen-lib" @@ -858,6 +860,122 @@ Please see the function `tempo-define-template'.") "*The template of a gen_fsm. Please see the function `tempo-define-template'.") +(defvar erlang-skel-gen-statem + '((erlang-skel-include erlang-skel-large-header) + "-behaviour(gen_statem)." n n + + "%% API" n + "-export([start_link/0])." n + n + "%% gen_statem callbacks" n + "-export([init/1, terminate/3, code_change/4])." n + "-export([state_name/3])." n + "-export([handle_event/4])." n + n + "-define(SERVER, ?MODULE)." n + n + "-record(data, {})." n + n + (erlang-skel-double-separator-start 3) + "%%% API" n + (erlang-skel-double-separator-end 3) n + (erlang-skel-separator-start 2) + "%% @doc" n + "%% Creates a gen_statem process which calls Module:init/1 to" n + "%% initialize. To ensure a synchronized start-up procedure, this" n + "%% function does not return until Module:init/1 has returned." n + "%%" n + (erlang-skel-separator-end 2) + "-spec start_link() ->" n> + "{ok, Pid :: pid()} |" n> + "ignore |" n> + "{error, Error :: term()}." n + "start_link() ->" n> + "gen_statem:start_link({local, ?SERVER}, ?MODULE, [], [])." n + n + (erlang-skel-double-separator-start 3) + "%%% gen_statem callbacks" n + (erlang-skel-double-separator-end 3) n + (erlang-skel-separator-start 2) + "%% @private" n + "%% @doc" n + "%% Whenever a gen_statem is started using gen_statem:start/[3,4] or" n + "%% gen_statem:start_link/[3,4], this function is called by the new" n + "%% process to initialize." n + (erlang-skel-separator-end 2) + "-spec init(Args :: term()) -> " n> + "{gen_statem:callback_mode()," n> + "State :: term(), Data :: term()} |" n> + "{gen_statem:callback_mode()," n> + "State :: term(), Data :: term()," n> + "[gen_statem:action()] | gen_statem:action()} |" n> + "ignore |" n> + "{stop, Reason :: term()}." n + "init([]) ->" n> + "{state_functions, state_name, #data{}}." n + n + (erlang-skel-separator-start 2) + "%% @private" n + "%% @doc" n + "%% If the gen_statem runs with CallbackMode =:= state_functions" n + "%% there should be one instance of this function for each possible" n + "%% state name. Whenever a gen_statem receives an event," n + "%% the instance of this function with the same name" n + "%% as the current state name StateName is called to" n + "%% handle the event." n + (erlang-skel-separator-end 2) + "-spec state_name(" n> + "gen_statem:event_type(), Msg :: term()," n> + "Data :: term()) ->" n> + "gen_statem:state_function_result(). " n + "state_name({call,Caller}, _Msg, Data) ->" n> + "{next_state, state_name, Data, [{reply,Caller,ok}]}." n + n + (erlang-skel-separator-start 2) + "%% @private" n + "%% @doc" n + "%% If the gen_statem runs with CallbackMode =:= handle_event_function" n + "%% this function is called for every event a gen_statem receives." n + (erlang-skel-separator-end 2) + "-spec handle_event(" n> + "gen_statem:event_type(), Msg :: term()," n> + "State :: term(), Data :: term()) ->" n> + "gen_statem:handle_event_result(). " n + "handle_event({call,From}, _Msg, State, Data) ->" n> + "{next_state, State, Data, [{reply,From,ok}]}." n + n + (erlang-skel-separator-start 2) + "%% @private" n + "%% @doc" n + "%% This function is called by a gen_statem when it is about to" n + "%% terminate. It should be the opposite of Module:init/1 and do any" n + "%% necessary cleaning up. When it returns, the gen_statem terminates with" n + "%% Reason. The return value is ignored." n + (erlang-skel-separator-end 2) + "-spec terminate(Reason :: term(), State :: term(), Data :: term()) ->" n> + "any()." n + "terminate(_Reason, _State, _Data) ->" n> + "void." n + n + (erlang-skel-separator-start 2) + "%% @private" n + "%% @doc" n + "%% Convert process state when code is changed" n + (erlang-skel-separator-end 2) + "-spec code_change(" n> + "OldVsn :: term() | {down,term()}," n> + "State :: term(), Data :: term(), Extra :: term()) ->" n> + "{ok, NewState :: term(), NewData :: term()}." n + "code_change(_OldVsn, State, Data, _Extra) ->" n> + "{ok, State, Data}." n + n + (erlang-skel-double-separator-start 3) + "%%% Internal functions" n + (erlang-skel-double-separator-end 3) + ) + "*The template of a gen_statem. +Please see the function `tempo-define-template'.") + (defvar erlang-skel-wx-object '((erlang-skel-include erlang-skel-large-header) "-behaviour(wx_object)." n n diff --git a/lib/tools/emacs/erlang.el b/lib/tools/emacs/erlang.el index 2ff14dea02..0a3fc0ddff 100644 --- a/lib/tools/emacs/erlang.el +++ b/lib/tools/emacs/erlang.el @@ -7,7 +7,7 @@ ;; %CopyrightBegin% ;; -;; Copyright Ericsson AB 1996-2014. All Rights Reserved. +;; Copyright Ericsson AB 1996-2016. All Rights Reserved. ;; ;; Licensed under the Apache License, Version 2.0 (the "License"); ;; you may not use this file except in compliance with the License. @@ -1345,7 +1345,7 @@ Lock syntax table. The effect is that `apply' in the atom ;;;###autoload -(defun erlang-mode () +(define-derived-mode erlang-mode prog-mode "Erlang" "Major mode for editing Erlang source files in Emacs. It knows about syntax and comment, it can indent code, it is capable of fontifying the source file, the TAGS commands are aware of Erlang @@ -1404,12 +1404,9 @@ and examples of hooks. Other commands: \\{erlang-mode-map}" - (interactive) - (kill-all-local-variables) - (setq major-mode 'erlang-mode) - (setq mode-name "Erlang") + ;; Use our own syntax table function + :syntax-table nil (erlang-syntax-table-init) - (use-local-map erlang-mode-map) (erlang-electric-init) (erlang-menu-init) (erlang-mode-variables) @@ -1419,12 +1416,8 @@ Other commands: (erlang-font-lock-init) (erlang-skel-init) (tempo-use-tag-list 'erlang-tempo-tags) - (run-hooks 'erlang-mode-hook) (if (zerop (buffer-size)) - (run-hooks 'erlang-new-file-hook)) - ;; Doesn't exist in Emacs v21.4; required by Emacs v23. - (if (boundp 'after-change-major-mode-hook) - (run-hooks 'after-change-major-mode-hook))) + (run-hooks 'erlang-new-file-hook))) ;;;###autoload (dolist (r '("\\.erl$" "\\.app\\.src$" "\\.escript" diff --git a/lib/tools/emacs/test.erl.indented b/lib/tools/emacs/test.erl.indented index 1986acadf1..6913068133 100644 --- a/lib/tools/emacs/test.erl.indented +++ b/lib/tools/emacs/test.erl.indented @@ -2,7 +2,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2009-2012. All Rights Reserved. +%% Copyright Ericsson AB 2009-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/emacs/test.erl.orig b/lib/tools/emacs/test.erl.orig index 7e8ad23412..621948cbe1 100644 --- a/lib/tools/emacs/test.erl.orig +++ b/lib/tools/emacs/test.erl.orig @@ -2,7 +2,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2009-2012. All Rights Reserved. +%% Copyright Ericsson AB 2009-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/Makefile b/lib/tools/src/Makefile index 7301ff856a..032bd612db 100644 --- a/lib/tools/src/Makefile +++ b/lib/tools/src/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 1996-2013. All Rights Reserved. +# Copyright Ericsson AB 1996-2016. All Rights Reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/lib/tools/src/cover.erl b/lib/tools/src/cover.erl index 87de31919f..69331732bf 100644 --- a/lib/tools/src/cover.erl +++ b/lib/tools/src/cover.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2001-2015. All Rights Reserved. +%% Copyright Ericsson AB 2001-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/eprof.erl b/lib/tools/src/eprof.erl index 0357e46a50..07e995993b 100644 --- a/lib/tools/src/eprof.erl +++ b/lib/tools/src/eprof.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1996-2013. All Rights Reserved. +%% Copyright Ericsson AB 1996-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/fprof.erl b/lib/tools/src/fprof.erl index c5c24c8eb3..b21eedc625 100644 --- a/lib/tools/src/fprof.erl +++ b/lib/tools/src/fprof.erl @@ -1567,13 +1567,20 @@ trace_handler({trace_ts, Pid, return_to, {_M, _F, Args} = MFArgs, TS} = Trace, trace_return_to(Table, Pid, Func, TS), TS; %% -%% spawn +%% spawn, only needed (and reliable) prior to 19.0 trace_handler({trace_ts, Pid, spawn, Child, MFArgs, TS} = Trace, Table, _, Dump) -> dump_stack(Dump, get(Pid), Trace), trace_spawn(Table, Child, MFArgs, TS, Pid), TS; %% +%% spawned, added in 19.0 +trace_handler({trace_ts, Pid, spawned, Parent, MFArgs, TS} = Trace, + Table, _, Dump) -> + dump_stack(Dump, get(Pid), Trace), + trace_spawn(Table, Pid, MFArgs, TS, Parent), + TS; +%% %% exit trace_handler({trace_ts, Pid, exit, _Reason, TS} = Trace, Table, _, Dump) -> @@ -1622,15 +1629,24 @@ trace_handler({trace_ts, Pid, in, {_M, _F, Args} = MFArgs, TS} = Trace, TS; %% %% gc_start -trace_handler({trace_ts, Pid, gc_start, _Func, TS} = Trace, - Table, _, Dump) -> +trace_handler({trace_ts, Pid, gc_minor_start, _Func, TS} = Trace, Table, _, Dump) -> + dump_stack(Dump, get(Pid), Trace), + trace_gc_start(Table, Pid, TS), + TS; + +trace_handler({trace_ts, Pid, gc_major_start, _Func, TS} = Trace, Table, _, Dump) -> dump_stack(Dump, get(Pid), Trace), trace_gc_start(Table, Pid, TS), TS; + %% %% gc_end -trace_handler({trace_ts, Pid, gc_end, _Func, TS} = Trace, - Table, _, Dump) -> +trace_handler({trace_ts, Pid, gc_minor_end, _Func, TS} = Trace, Table, _, Dump) -> + dump_stack(Dump, get(Pid), Trace), + trace_gc_end(Table, Pid, TS), + TS; + +trace_handler({trace_ts, Pid, gc_major_end, _Func, TS} = Trace, Table, _, Dump) -> dump_stack(Dump, get(Pid), Trace), trace_gc_end(Table, Pid, TS), TS; @@ -2014,8 +2030,10 @@ trace_spawn(Table, Pid, MFArgs, TS, Parent) -> ets:insert(Table, #proc{id = Pid, parent = Parent, spawned_as = MFArgs}); _ -> - throw({inconsistent_trace_data, ?MODULE, ?LINE, - [Pid, MFArgs, TS, Parent, Stack]}) + %% In 19.0 we get both a spawn and spawned event, + %% however we do not know the order so we just ignore + %% the second event that comes + ok end. diff --git a/lib/tools/src/instrument.erl b/lib/tools/src/instrument.erl index 34c5ba04cc..055f4a7afb 100644 --- a/lib/tools/src/instrument.erl +++ b/lib/tools/src/instrument.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1998-2009. All Rights Reserved. +%% Copyright Ericsson AB 1998-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/lcnt.erl b/lib/tools/src/lcnt.erl index d552d5b46e..78407a651a 100644 --- a/lib/tools/src/lcnt.erl +++ b/lib/tools/src/lcnt.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2010-2015. All Rights Reserved. +%% Copyright Ericsson AB 2010-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/tools.appup.src b/lib/tools/src/tools.appup.src index 9eee8df184..fa48fa4219 100644 --- a/lib/tools/src/tools.appup.src +++ b/lib/tools/src/tools.appup.src @@ -1,7 +1,7 @@ %% -*- erlang -*- %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2001-2014. All Rights Reserved. +%% Copyright Ericsson AB 2001-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/xref.erl b/lib/tools/src/xref.erl index 64add7afbb..32efa36fa2 100644 --- a/lib/tools/src/xref.erl +++ b/lib/tools/src/xref.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2000-2013. All Rights Reserved. +%% Copyright Ericsson AB 2000-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/xref_base.erl b/lib/tools/src/xref_base.erl index 88031f6e77..70eb107781 100644 --- a/lib/tools/src/xref_base.erl +++ b/lib/tools/src/xref_base.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2000-2013. All Rights Reserved. +%% Copyright Ericsson AB 2000-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/src/xref_parser.yrl b/lib/tools/src/xref_parser.yrl index 48602bb120..0711da79e2 100644 --- a/lib/tools/src/xref_parser.yrl +++ b/lib/tools/src/xref_parser.yrl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2000-2010. All Rights Reserved. +%% Copyright Ericsson AB 2000-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/test/Makefile b/lib/tools/test/Makefile index 8768413dc1..84c4e56aff 100644 --- a/lib/tools/test/Makefile +++ b/lib/tools/test/Makefile @@ -1,7 +1,7 @@ # # %CopyrightBegin% # -# Copyright Ericsson AB 1997-2012. All Rights Reserved. +# Copyright Ericsson AB 1997-2016. All Rights Reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/lib/tools/test/cover_SUITE.erl b/lib/tools/test/cover_SUITE.erl index d4b346c407..b4c9264b30 100644 --- a/lib/tools/test/cover_SUITE.erl +++ b/lib/tools/test/cover_SUITE.erl @@ -23,51 +23,43 @@ -include_lib("common_test/include/ct.hrl"). -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}]. all() -> NoStartStop = [eif,otp_5305,otp_5418,otp_7095,otp_8273, otp_8340,otp_8188,compile_beam_opts,eep37, - analyse_no_beam, line_0, compile_beam_no_file, + analyse_no_beam, line_0, compile_beam_no_file, otp_13277, otp_13289], StartStop = [start, compile, analyse, misc, stop, - distribution, reconnect, die_and_reconnect, - dont_reconnect_after_stop, stop_node_after_disconnect, - export_import, otp_5031, otp_6115, - otp_8270, otp_10979_hanging_node], + distribution, reconnect, die_and_reconnect, + dont_reconnect_after_stop, stop_node_after_disconnect, + export_import, otp_5031, otp_6115, + otp_8270, otp_10979_hanging_node], case whereis(cover_server) of - undefined -> - [coverage,StartStop ++ NoStartStop]; - _pid -> - [coverage|NoStartStop++[coverage_analysis]] + undefined -> + [coverage,StartStop ++ NoStartStop]; + _pid -> + [coverage|NoStartStop++[coverage_analysis]] end. -groups() -> - []. - init_per_suite(Config) -> [{ct_is_running_cover,whereis(cover_server) =/= undefined}|Config]. end_per_suite(_Config) -> ok. -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - init_per_testcase(TC, Config) when TC =:= misc; - TC =:= compile; - TC =:= analyse; - TC =:= distribution; - TC =:= otp_5031; - TC =:= stop -> + TC =:= compile; + TC =:= analyse; + TC =:= distribution; + TC =:= otp_5031; + TC =:= stop -> case code:which(crypto) of - Path when is_list(Path) -> - init_per_testcase(dummy_tc, Config); - _Else -> - {skip, "No crypto file to test with"} + Path when is_list(Path) -> + init_per_testcase(dummy_tc, Config); + _Else -> + {skip, "No crypto file to test with"} end; init_per_testcase(_TestCase, Config) -> Config. @@ -75,10 +67,10 @@ init_per_testcase(_TestCase, Config) -> end_per_testcase(TestCase, Config) -> NoStop = [start,compile,analyse,misc], DontStop = proplists:get_bool(ct_is_running_cover, Config) orelse - lists:member(TestCase, NoStop), + lists:member(TestCase, NoStop), case DontStop of - true -> ok; - false -> cover:stop() + true -> ok; + false -> cover:stop() end, ok. @@ -87,7 +79,7 @@ coverage(Config) when is_list(Config) -> ?MODULE:do_coverage(Config). do_coverage(Config) -> - Outdir = ?config(priv_dir, Config), + Outdir = proplists:get_value(priv_dir, Config), ExportFile = filename:join(Outdir, "export"), ok = cover:export(ExportFile, ?MODULE), {error,{already_started,_}} = cover:start(), @@ -100,16 +92,16 @@ do_coverage(Config) -> %% Cover escaping of '&' in HTML files. case proplists:get_bool(ct_is_running_cover, Config) of - false -> - %% Cover server was implicitly started when this module - %% was cover-compiled. We must stop the cover server, but - %% we must ensure that this module is not on the call - %% stack when it is unloaded. Therefore, the call that - %% follows MUST be tail-recursive. - cover:stop(); - true -> - %% Cover server was started by common_test; don't stop it. - ok + false -> + %% Cover server was implicitly started when this module + %% was cover-compiled. We must stop the cover server, but + %% we must ensure that this module is not on the call + %% stack when it is unloaded. Therefore, the call that + %% follows MUST be tail-recursive. + cover:stop(); + true -> + %% Cover server was started by common_test; don't stop it. + ok end. %% This test case will only be run when common_test is running cover. @@ -120,7 +112,7 @@ coverage_analysis(Config) when is_list(Config) -> io:format("~p\n", [Analysis2]), {ok,_Analysis3} = cover:analyze(?MODULE, calls, line), - Outdir = ?config(priv_dir, Config), + Outdir = proplists:get_value(priv_dir, Config), Outfile = filename:join(Outdir, ?MODULE), {ok,Outfile} = cover:analyze_to_file(?MODULE, Outfile), @@ -130,92 +122,90 @@ coverage_analysis(Config) when is_list(Config) -> {ok,Outfile} = cover:analyze_to_file(?MODULE, Outfile, [html]), ok. -start(suite) -> []; start(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(data_dir, Config)), + ok = file:set_cwd(proplists:get_value(data_dir, Config)), - ?line Files = lsfiles(), - ?line remove(files(Files, ".out")), + Files = lsfiles(), + remove(files(Files, ".out")), - ?line {ok, Pid} = cover:start(), - ?line {error, {already_started, Pid}} = cover:start(). + {ok, Pid} = cover:start(), + {error, {already_started, Pid}} = cover:start(). -compile(suite) -> []; compile(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(data_dir, Config)), + ok = file:set_cwd(proplists:get_value(data_dir, Config)), - ?line Result1 = cover:compile_directory(), - ?line SortedResult = lists:sort(Result1), - ?line {ok, CWD} = file:get_cwd(), - ?line Result2 = cover:compile_directory(CWD), - ?line SortedResult = lists:sort(Result2), - ?line [{error,DFile},{ok,a},{ok,b},{ok,cc},{ok,f}] = SortedResult, - ?line [{ok,e}] = cover:compile_directory("d1"), - ?line {error,enoent} = cover:compile_directory("d2"), + Result1 = cover:compile_directory(), + SortedResult = lists:sort(Result1), + {ok, CWD} = file:get_cwd(), + Result2 = cover:compile_directory(CWD), + SortedResult = lists:sort(Result2), + [{error,DFile},{ok,a},{ok,b},{ok,cc},{ok,f}] = SortedResult, + [{ok,e}] = cover:compile_directory("d1"), + {error,enoent} = cover:compile_directory("d2"), [] = cover:compile([]), Result21 = cover:compile([a,b,"cc.erl",d,"f"]), SortedResult21 = lists:sort(Result21), [{error,DFile},{ok,a},{ok,b},{ok,cc},{ok,f}] = SortedResult21, - ?line {ok,a} = cover:compile(a), - ?line {ok,b} = compile:file(b), - ?line code:purge(b), - ?line {module,b} = code:load_file(b), - ?line {ok,d} = cover:compile("d.erl", [{d,'AGE',42}]), - ?line {error,_BBFile} = cover:compile(bb), + {ok,a} = cover:compile(a), + {ok,b} = compile:file(b), + code:purge(b), + {module,b} = code:load_file(b), + {ok,d} = cover:compile("d.erl", [{d,'AGE',42}]), + {error,_BBFile} = cover:compile(bb), - ?line StdlibDir = code:lib_dir(stdlib), - ?line Lists = filename:join([StdlibDir, "src", "lists.erl"]), - ?line {error, Lists} = cover:compile(Lists), + StdlibDir = code:lib_dir(stdlib), + Lists = filename:join([StdlibDir, "src", "lists.erl"]), + {error, Lists} = cover:compile(Lists), %% For compiling beam: using dummy files v,w,x,y and z - ?line file:set_cwd("compile_beam"), - ?line {ok,_} = compile:file(v,[debug_info,report]), - ?line {ok,_} = compile:file(w,[debug_info,report]), - ?line {ok,_} = compile:file(x), - ?line {ok,_} = compile:file("d/y",[debug_info,{outdir,"d"},report]), - ?line Key = "A Krypto Key", + file:set_cwd("compile_beam"), + {ok,_} = compile:file(v,[debug_info,report]), + {ok,_} = compile:file(w,[debug_info,report]), + {ok,_} = compile:file(x), + {ok,_} = compile:file("d/y",[debug_info,{outdir,"d"},report]), + Key = "A Krypto Key", CryptoWorks = crypto_works(), case CryptoWorks of - false -> - {ok,_} = compile:file(crypt, [debug_info,report]), - {ok,crypt} = cover:compile_beam("crypt.beam"); - true -> - {ok,_} = compile:file(crypt, [{debug_info_key,Key},report]), - {error,{encrypted_abstract_code,_}} = - cover:compile_beam("crypt.beam"), - ok = beam_lib:crypto_key_fun(simple_crypto_fun(Key)), - {ok,crypt} = cover:compile_beam("crypt.beam") + false -> + {ok,_} = compile:file(crypt, [debug_info,report]), + {ok,crypt} = cover:compile_beam("crypt.beam"); + true -> + {ok,_} = compile:file(crypt, [{debug_info_key,Key},report]), + {error,{encrypted_abstract_code,_}} = + cover:compile_beam("crypt.beam"), + ok = beam_lib:crypto_key_fun(simple_crypto_fun(Key)), + {ok,crypt} = cover:compile_beam("crypt.beam") end, - Path = filename:join([?config(data_dir, Config), "compile_beam", "v.erl"]), - ?line {ok,v} = cover:compile_beam(v), + Path = filename:join([proplists:get_value(data_dir, Config), "compile_beam", "v.erl"]), + {ok,v} = cover:compile_beam(v), {source,Path} = lists:keyfind(source, 1, v:module_info(compile)), - ?line {ok,w} = cover:compile_beam("w.beam"), - ?line {error,{no_abstract_code,"./x.beam"}} = cover:compile_beam(x), - ?line {error,{already_cover_compiled,no_beam_found,a}}=cover:compile_beam(a), - ?line {error,non_existing} = cover:compile_beam(z), - ?line [{ok,y}] = cover:compile_beam_directory("d"), - ?line Result3 = lists:sort(cover:compile_beam_directory()), - ?line [{error,{no_abstract_code,XBeam}},{ok,crypt},{ok,v},{ok,w}] = Result3, - ?line {error,enoent} = cover:compile_beam_directory("d2"), + {ok,w} = cover:compile_beam("w.beam"), + {error,{no_abstract_code,"./x.beam"}} = cover:compile_beam(x), + {error,{already_cover_compiled,no_beam_found,a}}=cover:compile_beam(a), + {error,non_existing} = cover:compile_beam(z), + [{ok,y}] = cover:compile_beam_directory("d"), + Result3 = lists:sort(cover:compile_beam_directory()), + [{error,{no_abstract_code,XBeam}},{ok,crypt},{ok,v},{ok,w}] = Result3, + {error,enoent} = cover:compile_beam_directory("d2"), [] = cover:compile_beam([]), Result31 = cover:compile_beam([crypt,"v.beam",w,"x"]), SortedResult31 = lists:sort(Result31), [{error,{no_abstract_code,XBeam}},{ok,crypt},{ok,v},{ok,w}] = SortedResult31, - ?line decompile([v,w,y]), - ?line Files = lsfiles(), - ?line remove(files(Files, ".beam")). + decompile([v,w,y]), + Files = lsfiles(), + remove(files(Files, ".beam")). crypto_works() -> try crypto:start() of - {error,{already_started,crypto}} -> true; - ok -> true + {error,{already_started,crypto}} -> true; + ok -> true catch - error:_ -> - false + error:_ -> + false end. simple_crypto_fun(Key) -> @@ -223,90 +213,89 @@ simple_crypto_fun(Key) -> ({debug_info, des3_cbc, crypt, _}) -> Key end. -analyse(suite) -> []; analyse(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(data_dir, Config)), + ok = file:set_cwd(proplists:get_value(data_dir, Config)), - ?line done = a:start(5), + done = a:start(5), {ok, {a,{17,2}}=ACovMod} = cover:analyse(a, coverage, module), {ok, [{{a,exit_kalle,0},{1,0}}, - {{a,loop,3},{5,1}}, - {{a,pong,1},{1,0}}, - {{a,start,1},{6,0}}, - {{a,stop,1},{0,1}}, - {{a,trycatch,1},{4,0}}]=ACovFunc} = - cover:analyse(a, coverage, function), + {{a,loop,3},{5,1}}, + {{a,pong,1},{1,0}}, + {{a,start,1},{6,0}}, + {{a,stop,1},{0,1}}, + {{a,trycatch,1},{4,0}}]=ACovFunc} = + cover:analyse(a, coverage, function), {ok, [{{a,exit_kalle,0,1},{1,0}}, - {{a,loop,3,1},{3,1}}, - {{a,loop,3,2},{2,0}}, - {{a,pong,1,1},{1,0}}, - {{a,start,1,1},{6,0}}, - {{a,stop,1,1},{0,1}}, - {{a,trycatch,1,1},{4,0}}]=ACovClause} = - cover:analyse(a, coverage, clause), - ?line {ok, [{{a,9},{1,0}}, - {{a,10},{1,0}}, - {{a,11},{1,0}}, - {{a,13},{1,0}}, - {{a,14},{1,0}}, - {{a,15},{1,0}}, - {{a,21},{0,1}}, - {{a,26},{1,0}}, - {{a,31},{1,0}}, - {{a,32},{1,0}}, - {{a,34},{1,0}}, - {{a,36},{0,1}}, - {{a,39},{1,0}}, - {{a,40},{1,0}}, - {{a,44},{1,0}}, - {{a,47},{1,0}}, - {{a,49},{1,0}}, - {{a,51},{1,0}}, - {{a,55},{1,0}}]=ACovLine} = cover:analyse(a, coverage, line), + {{a,loop,3,1},{3,1}}, + {{a,loop,3,2},{2,0}}, + {{a,pong,1,1},{1,0}}, + {{a,start,1,1},{6,0}}, + {{a,stop,1,1},{0,1}}, + {{a,trycatch,1,1},{4,0}}]=ACovClause} = + cover:analyse(a, coverage, clause), + {ok, [{{a,9},{1,0}}, + {{a,10},{1,0}}, + {{a,11},{1,0}}, + {{a,13},{1,0}}, + {{a,14},{1,0}}, + {{a,15},{1,0}}, + {{a,21},{0,1}}, + {{a,26},{1,0}}, + {{a,31},{1,0}}, + {{a,32},{1,0}}, + {{a,34},{1,0}}, + {{a,36},{0,1}}, + {{a,39},{1,0}}, + {{a,40},{1,0}}, + {{a,44},{1,0}}, + {{a,47},{1,0}}, + {{a,49},{1,0}}, + {{a,51},{1,0}}, + {{a,55},{1,0}}]=ACovLine} = cover:analyse(a, coverage, line), {ok, {a,15}=ACallsMod} = cover:analyse(a, calls, module), {ok, [{{a,exit_kalle,0},1}, - {{a,loop,3},6}, - {{a,pong,1},5}, - {{a,start,1},1}, - {{a,stop,1},0}, - {{a,trycatch,1},2}]=ACallsFunc} = cover:analyse(a, calls, function), + {{a,loop,3},6}, + {{a,pong,1},5}, + {{a,start,1},1}, + {{a,stop,1},0}, + {{a,trycatch,1},2}]=ACallsFunc} = cover:analyse(a, calls, function), {ok, [{{a,exit_kalle,0,1},1}, - {{a,loop,3,1},5}, - {{a,loop,3,2},1}, - {{a,pong,1,1},5}, - {{a,start,1,1},1}, - {{a,stop,1,1},0}, - {{a,trycatch,1,1},2}]=ACallsClause} = cover:analyse(a, calls, clause), - ?line {ok, [{{a,9},1}, - {{a,10},1}, - {{a,11},1}, - {{a,13},1}, - {{a,14},1}, - {{a,15},1}, - {{a,21},0}, - {{a,26},5}, - {{a,31},5}, - {{a,32},5}, - {{a,34},5}, - {{a,36},0}, - {{a,39},1}, - {{a,40},1}, - {{a,44},2}, - {{a,47},1}, - {{a,49},1}, - {{a,51},2}, - {{a,55},1}]=ACallsLine} = cover:analyse(a, calls, line), + {{a,loop,3,1},5}, + {{a,loop,3,2},1}, + {{a,pong,1,1},5}, + {{a,start,1,1},1}, + {{a,stop,1,1},0}, + {{a,trycatch,1,1},2}]=ACallsClause} = cover:analyse(a, calls, clause), + {ok, [{{a,9},1}, + {{a,10},1}, + {{a,11},1}, + {{a,13},1}, + {{a,14},1}, + {{a,15},1}, + {{a,21},0}, + {{a,26},5}, + {{a,31},5}, + {{a,32},5}, + {{a,34},5}, + {{a,36},0}, + {{a,39},1}, + {{a,40},1}, + {{a,44},2}, + {{a,47},1}, + {{a,49},1}, + {{a,51},2}, + {{a,55},1}]=ACallsLine} = cover:analyse(a, calls, line), {ok,ACovFunc} = cover:analyse(a), {ok,ACovMod} = cover:analyse(a, module), {ok,ACallsFunc} = cover:analyse(a, calls), - ?line {ok, "a.COVER.out"} = cover:analyse_to_file(a), - ?line {ok, "e.COVER.out"} = cover:analyse_to_file(e), - ?line {ok, "a.COVER.html"} = cover:analyse_to_file(a,[html]), - ?line {ok, "e.COVER.html"} = cover:analyse_to_file(e,[html]), + {ok, "a.COVER.out"} = cover:analyse_to_file(a), + {ok, "e.COVER.out"} = cover:analyse_to_file(e), + {ok, "a.COVER.html"} = cover:analyse_to_file(a,[html]), + {ok, "e.COVER.html"} = cover:analyse_to_file(e,[html]), %% Analyse all modules Modules = cover:modules(), @@ -355,7 +344,7 @@ analyse(Config) when is_list(Config) -> {result,CovClause1,[]} = cover:analyse(Modules,coverage,clause), true = lists:sort(CovClause) == lists:sort(CovClause1), - + {result,CovLine1,[]} = cover:analyse(Modules,coverage,line), true = lists:sort(CovLine) == lists:sort(CovLine1), @@ -377,18 +366,18 @@ analyse(Config) when is_list(Config) -> true = lists:sort(AllToFileHtml) == lists:sort(AllToFileHtml1), %% analyse_to_file of file which is compiled from beam - ?line {ok,f} = compile:file(f,[debug_info]), - ?line code:purge(f), - ?line {module,f} = code:load_file(f), - ?line {ok,f} = cover:compile_beam(f), - ?line f:f2(), - ?line {ok, "f.COVER.out"} = cover:analyse_to_file(f), + {ok,f} = compile:file(f,[debug_info]), + code:purge(f), + {module,f} = code:load_file(f), + {ok,f} = cover:compile_beam(f), + f:f2(), + {ok, "f.COVER.out"} = cover:analyse_to_file(f), %% Source code can be found via source - ?line {ok,v} = compile:file("compile_beam/v",[debug_info]), - ?line code:purge(v), - ?line {module,v} = code:load_file(v), - ?line {ok,v} = cover:compile_beam(v), + {ok,v} = compile:file("compile_beam/v",[debug_info]), + code:purge(v), + {module,v} = code:load_file(v), + {ok,v} = cover:compile_beam(v), {ok,"v.COVER.out"} = cover:analyse_to_file(v), %% Source code cannot be found @@ -403,163 +392,161 @@ analyse(Config) when is_list(Config) -> code:purge(z), code:delete(z), - ?line {error,{not_cover_compiled,b}} = cover:analyse(b), - ?line {error,{not_cover_compiled,g}} = cover:analyse(g), + {error,{not_cover_compiled,b}} = cover:analyse(b), + {error,{not_cover_compiled,g}} = cover:analyse(g), {result,[],[{not_cover_compiled,b}]} = cover:analyse([b]), - ?line {error,{not_cover_compiled,b}} = cover:analyse_to_file(b), + {error,{not_cover_compiled,b}} = cover:analyse_to_file(b), {error,{not_cover_compiled,g}} = cover:analyse_to_file(g), {result,[],[{not_cover_compiled,g}]} = cover:analyse_to_file([g]). -misc(suite) -> []; misc(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(data_dir, Config)), + ok = file:set_cwd(proplists:get_value(data_dir, Config)), - ?line [a,cc,crypt,d,e,f,v] = lists:sort(cover:modules()), + [a,cc,crypt,d,e,f,v] = lists:sort(cover:modules()), - ?line {ok,cc} = compile:file(cc), - ?line code:purge(cc), - ?line {module,cc} = code:load_file(cc), - ?line [a,crypt,d,e,f,v] = lists:sort(cover:modules()), + {ok,cc} = compile:file(cc), + code:purge(cc), + {module,cc} = code:load_file(cc), + [a,crypt,d,e,f,v] = lists:sort(cover:modules()), - ?line {file, _File} = cover:is_compiled(a), - ?line false = cover:is_compiled(b), - ?line false = cover:is_compiled(g), + {file, _File} = cover:is_compiled(a), + false = cover:is_compiled(b), + false = cover:is_compiled(g), - ?line ok = cover:reset(a), - ?line {ok, {a,{0,19}}} = cover:analyse(a, module), - ?line ok = cover:reset(). + ok = cover:reset(a), + {ok, {a,{0,19}}} = cover:analyse(a, module), + ok = cover:reset(). -stop(suite) -> []; stop(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(data_dir, Config)), - - ?line cover_compiled = code:which(a), - ?line {ok,d} = compile:file(d, [{d,'AGE',42}]), - ?line code:purge(d), - ?line {module,d} = code:load_file(d), - ?line ok = cover:stop(), - ?line Beam = code:which(a), - ?line true = is_unloaded(Beam), - - ?line Files = lsfiles(), - ?line remove(files(Files, ".out")), - ?line remove(files(Files, ".html")), - ?line remove(files(Files, ".beam")). - -distribution(suite) -> []; + ok = file:set_cwd(proplists:get_value(data_dir, Config)), + + cover_compiled = code:which(a), + {ok,d} = compile:file(d, [{d,'AGE',42}]), + code:purge(d), + {module,d} = code:load_file(d), + ok = cover:stop(), + Beam = code:which(a), + true = is_unloaded(Beam), + + Files = lsfiles(), + remove(files(Files, ".out")), + remove(files(Files, ".html")), + remove(files(Files, ".beam")). + distribution(Config) when is_list(Config) -> - ?line DataDir = ?config(data_dir, Config), - ?line ok = file:set_cwd(DataDir), + DataDir = proplists:get_value(data_dir, Config), + ok = file:set_cwd(DataDir), - ?line {ok,N1} = ?t:start_node(cover_SUITE_distribution1,slave,[]), - ?line {ok,N2} = ?t:start_node(cover_SUITE_distribution2,slave,[]), - ?line {ok,N3} = ?t:start_node(cover_SUITE_distribution3,slave,[]), - ?line {ok,N4} = ?t:start_node(cover_SUITE_distribution4,slave,[]), + {ok,N1} = test_server:start_node(cover_SUITE_distribution1,slave,[]), + {ok,N2} = test_server:start_node(cover_SUITE_distribution2,slave,[]), + {ok,N3} = test_server:start_node(cover_SUITE_distribution3,slave,[]), + {ok,N4} = test_server:start_node(cover_SUITE_distribution4,slave,[]), %% Check that an already compiled module is loaded on new nodes - ?line {ok,f} = cover:compile(f), - ?line {ok,[_,_,_,_]} = cover:start(nodes()), - ?line cover_compiled = code:which(f), - ?line cover_compiled = rpc:call(N1,code,which,[f]), - ?line cover_compiled = rpc:call(N2,code,which,[f]), - ?line cover_compiled = rpc:call(N3,code,which,[f]), - ?line cover_compiled = rpc:call(N4,code,which,[f]), + {ok,f} = cover:compile(f), + {ok,[_,_,_,_]} = cover:start(nodes()), + cover_compiled = code:which(f), + cover_compiled = rpc:call(N1,code,which,[f]), + cover_compiled = rpc:call(N2,code,which,[f]), + cover_compiled = rpc:call(N3,code,which,[f]), + cover_compiled = rpc:call(N4,code,which,[f]), %% Check that a node cannot be started twice - ?line {ok,[]} = cover:start(N2), + {ok,[]} = cover:start(N2), %% Check that the current node (i.e. the main node) is not started with %% start/1 and not stopped with stop/1 - ?line {ok,[]} = cover:start(node()), - ?line ok = cover:stop(node()), - ?line true = is_pid(whereis(cover_server)), + {ok,[]} = cover:start(node()), + ok = cover:stop(node()), + true = is_pid(whereis(cover_server)), %% Check that a new compiled module is loaded on all existing nodes - ?line compile:file("compile_beam/v",[debug_info]), - ?line {ok,v} = cover:compile_beam(v), - ?line cover_compiled = code:which(v), - ?line cover_compiled = rpc:call(N1,code,which,[v]), - ?line cover_compiled = rpc:call(N2,code,which,[v]), - ?line cover_compiled = rpc:call(N3,code,which,[v]), - ?line cover_compiled = rpc:call(N4,code,which,[v]), - + compile:file("compile_beam/v",[debug_info]), + {ok,v} = cover:compile_beam(v), + cover_compiled = code:which(v), + cover_compiled = rpc:call(N1,code,which,[v]), + cover_compiled = rpc:call(N2,code,which,[v]), + cover_compiled = rpc:call(N3,code,which,[v]), + cover_compiled = rpc:call(N4,code,which,[v]), + %% this is lost when the node is killed - ?line rpc:call(N3,f,f2,[]), - ?line rpc:call(N3,erlang,halt,[]), + rpc:call(N3,f,f2,[]), + rpc:call(N3,erlang,halt,[]), %% this should be visible in analyse - ?line rpc:call(N1,f,f1,[]), + rpc:call(N1,f,f1,[]), %% Check that data is collected from remote node when stopped - ?line ok = cover:stop(N1), - ?line N1Beam = rpc:call(N1,code,which,[f]), - ?line true = is_unloaded(N1Beam), - ?line check_f_calls(1,0), + ok = cover:stop(N1), + N1Beam = rpc:call(N1,code,which,[f]), + true = is_unloaded(N1Beam), + check_f_calls(1,0), %% Call f:f1() again on another node and check that number of calls is %% accumulated. - ?line f:f1(), - ?line check_f_calls(2,0), - + f:f1(), + check_f_calls(2,0), + %% Check that reset works on all nodes - ?line f:f1(), - ?line rpc:call(N2,f,f1,[]), - ?line ok = cover:reset(f), - ?line check_f_calls(0,0), - + f:f1(), + rpc:call(N2,f,f1,[]), + ok = cover:reset(f), + check_f_calls(0,0), + %% Check that data is collected from all nodes - ?line rpc:call(N2,f,f1,[]), - ?line f:f2(), - ?line check_f_calls(1,1), + rpc:call(N2,f,f1,[]), + f:f2(), + check_f_calls(1,1), %% Check that same data is not fetched again (i.e. that analyse does %% reset on the remote node(s)) - ?line check_f_calls(1,1), + check_f_calls(1,1), %% Another checn that data is not fetched twice, i.e. when flushed %% then analyse should not add the same data again. - ?line rpc:call(N4,f,f2,[]), - ?line ok = cover:flush(N4), - ?line check_f_calls(1,2), + rpc:call(N4,f,f2,[]), + ok = cover:flush(N4), + check_f_calls(1,2), %% Check that flush collects data so calls are not lost if node is killed - ?line rpc:call(N4,f,f2,[]), - ?line ok = cover:flush(N4), - ?line rpc:call(N4,erlang,halt,[]), - ?line check_f_calls(1,3), + rpc:call(N4,f,f2,[]), + ok = cover:flush(N4), + rpc:call(N4,erlang,halt,[]), + check_f_calls(1,3), %% Check that stop() unloads on all nodes - ?line ok = cover:stop(), - ?line timer:sleep(100), %% Give nodes time to unload on slow machines. - ?line LocalBeam = code:which(f), - ?line N2Beam = rpc:call(N2,code,which,[f]), - ?line true = is_unloaded(LocalBeam), - ?line true = is_unloaded(N2Beam), + ok = cover:stop(), + timer:sleep(100), %% Give nodes time to unload on slow machines. + LocalBeam = code:which(f), + N2Beam = rpc:call(N2,code,which,[f]), + true = is_unloaded(LocalBeam), + true = is_unloaded(N2Beam), %% Check that cover_server on remote node does not die if main node dies - ?line {ok,[N1]} = cover:start(N1), - ?line true = is_pid(N1Server = rpc:call(N1,erlang,whereis,[cover_server])), - ?line exit(whereis(cover_server),kill), - ?line timer:sleep(100), - ?line N1Server = rpc:call(N1,erlang,whereis,[cover_server]), + {ok,[N1]} = cover:start(N1), + true = is_pid(N1Server = rpc:call(N1,erlang,whereis,[cover_server])), + exit(whereis(cover_server),kill), + timer:sleep(100), + N1Server = rpc:call(N1,erlang,whereis,[cover_server]), %% Cleanup - ?line Files = lsfiles(), - ?line remove(files(Files, ".beam")), - ?line ?t:stop_node(N1), - ?line ?t:stop_node(N2). + Files = lsfiles(), + remove(files(Files, ".beam")), + test_server:stop_node(N1), + test_server:stop_node(N2). %% Test that a lost node is reconnected reconnect(Config) -> - DataDir = ?config(data_dir, Config), + DataDir = proplists:get_value(data_dir, Config), ok = file:set_cwd(DataDir), {ok,a} = compile:file(a), {ok,b} = compile:file(b), {ok,f} = compile:file(f), - {ok,N1} = ?t:start_node(cover_SUITE_reconnect,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(cover_SUITE_reconnect,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), {ok,a} = cover:compile(a), {ok,f} = cover:compile(f), {ok,[N1]} = cover:start(nodes()), @@ -600,19 +587,20 @@ reconnect(Config) -> check_f_calls(2,1), cover:stop(), - ?t:stop_node(N1), + test_server:stop_node(N1), ok. %% Test that a lost node is reconnected - also if it has been dead die_and_reconnect(Config) -> - DataDir = ?config(data_dir, Config), + DataDir = proplists:get_value(data_dir, Config), ok = file:set_cwd(DataDir), {ok,f} = compile:file(f), NodeName = cover_SUITE_die_and_reconnect, - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), %% {ok,a} = cover:compile(a), {ok,f} = cover:compile(f), {ok,[N1]} = cover:start(nodes()), @@ -629,8 +617,9 @@ die_and_reconnect(Config) -> check_f_calls(1,0), % only the first call - before the flush %% Restart the node and check that cover reconnects - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), timer:sleep(100), [N1] = cover:which_nodes(), % we are reconnected cover_compiled = rpc:call(N1,code,which,[f]), @@ -642,20 +631,21 @@ die_and_reconnect(Config) -> check_f_calls(2,0), cover:stop(), - ?t:stop_node(N1), + test_server:stop_node(N1), ok. %% Test that a stopped node is not marked as lost, i.e. that it is not %% reconnected if it is restarted (OTP-10638) dont_reconnect_after_stop(Config) -> - DataDir = ?config(data_dir, Config), + DataDir = proplists:get_value(data_dir, Config), ok = file:set_cwd(DataDir), {ok,f} = compile:file(f), NodeName = cover_SUITE_dont_reconnect_after_stop, - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), {ok,f} = cover:compile(f), {ok,[N1]} = cover:start(nodes()), @@ -670,8 +660,9 @@ dont_reconnect_after_stop(Config) -> check_f_calls(1,0), %% Restart the node and check that cover does not reconnect - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), timer:sleep(300), cover_which_nodes([]), Beam = rpc:call(N1,code,which,[f]), @@ -685,20 +676,21 @@ dont_reconnect_after_stop(Config) -> check_f_calls(1,0), cover:stop(), - ?t:stop_node(N1), + test_server:stop_node(N1), ok. %% Test that a node which is stopped while it is marked as lost is not %% reconnected if it is restarted (OTP-10638) stop_node_after_disconnect(Config) -> - DataDir = ?config(data_dir, Config), + DataDir = proplists:get_value(data_dir, Config), ok = file:set_cwd(DataDir), {ok,f} = compile:file(f), NodeName = cover_SUITE_stop_node_after_disconnect, - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), {ok,f} = cover:compile(f), {ok,[N1]} = cover:start(nodes()), @@ -715,8 +707,9 @@ stop_node_after_disconnect(Config) -> cover:stop(N1), %% Restart the node and check that cover does not reconnect - {ok,N1} = ?t:start_node(NodeName,peer, - [{args," -pa " ++ DataDir},{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer, + [{args," -pa " ++ DataDir}, + {start_cover,false}]), timer:sleep(300), cover_which_nodes([]), Beam = rpc:call(N1,code,which,[f]), @@ -730,11 +723,11 @@ stop_node_after_disconnect(Config) -> check_f_calls(1,0), cover:stop(), - ?t:stop_node(N1), + test_server:stop_node(N1), ok. distribution_performance(Config) -> - PrivDir = ?config(priv_dir,Config), + PrivDir = proplists:get_value(priv_dir,Config), Dir = filename:join(PrivDir,"distribution_performance"), AllFiles = filename:join(Dir,"*"), ok = filelib:ensure_dir(AllFiles), @@ -744,16 +737,16 @@ distribution_performance(Config) -> C = 10, % and each function of C clauses Mods = generate_modules(M,F,C,Dir), -% ?t:break(""), + % test_server:break(""), NodeName = cover_SUITE_distribution_performance, - {ok,N1} = ?t:start_node(NodeName,peer,[{start_cover,false}]), + {ok,N1} = test_server:start_node(NodeName,peer,[{start_cover,false}]), %% CFun = fun() -> %% [{ok,_} = cover:compile_beam(Mod) || Mod <- Mods] %% end, CFun = fun() -> cover:compile_beam(Mods) end, {CT,_CA} = timer:tc(CFun), -% erlang:display(_CA), + % erlang:display(_CA), erlang:display({compile,CT}), {SNT,_} = timer:tc(fun() -> {ok,[N1]} = cover:start(nodes()) end), @@ -761,27 +754,27 @@ distribution_performance(Config) -> [1 = rpc:call(N1,Mod,f1,[1]) || Mod <- Mods], -% Fun = fun() -> [cover:analyse(Mod,calls,function) || Mod<-Mods] end, -% Fun = fun() -> analyse_all(Mods,calls,function) end, -% Fun = fun() -> cover:analyse('_',calls,function) end, + % Fun = fun() -> [cover:analyse(Mod,calls,function) || Mod<-Mods] end, + % Fun = fun() -> analyse_all(Mods,calls,function) end, + % Fun = fun() -> cover:analyse('_',calls,function) end, Fun = fun() -> cover:analyse(Mods,calls,function) end, -% Fun = fun() -> [begin cover:analyse_to_file(Mod,[html]) end || Mod<-Mods] end, -% Fun = fun() -> analyse_all_to_file(Mods,[html]) end, -% Fun = fun() -> cover:analyse_to_file(Mods,[html]) end, -% Fun = fun() -> cover:analyse_to_file([html]) end, + % Fun = fun() -> [begin cover:analyse_to_file(Mod,[html]) end || Mod<-Mods] end, + % Fun = fun() -> analyse_all_to_file(Mods,[html]) end, + % Fun = fun() -> cover:analyse_to_file(Mods,[html]) end, + % Fun = fun() -> cover:analyse_to_file([html]) end, -% Fun = fun() -> cover:reset() end, + % Fun = fun() -> cover:reset() end, {AT,_A} = timer:tc(Fun), erlang:display({analyse,AT}), -% erlang:display(lists:sort([X || X={_MFA,N} <- lists:append([L || {ok,L}<-A]), N=/=0])), + % erlang:display(lists:sort([X || X={_MFA,N} <- lists:append([L || {ok,L}<-A]), N=/=0])), %% fprof:apply(Fun, [],[{procs,[whereis(cover_server)]}]), %% fprof:profile(), %% fprof:analyse(dest,[]), - {SNT2,_} = timer:tc(fun() -> ?t:stop_node(N1) end), + {SNT2,_} = timer:tc(fun() -> test_server:stop_node(N1) end), erlang:display({stop_node,SNT2}), code:del_path(Dir), @@ -793,10 +786,10 @@ distribution_performance(Config) -> %% Run analysis in parallel analyse_all(Mods,Analysis,Level) -> Pids = [begin - Pid = spawn(fun() -> - {ok,A} = cover:analyse(Mod,Analysis,Level), - exit(A) - end), + Pid = spawn(fun() -> + {ok,A} = cover:analyse(Mod,Analysis,Level), + exit(A) + end), erlang:monitor(process,Pid), Pid end || Mod <- Mods], @@ -804,18 +797,18 @@ analyse_all(Mods,Analysis,Level) -> analyse_all_to_file(Mods,Opts) -> Pids = [begin - Pid = cover:async_analyse_to_file(Mod,Opts), - erlang:monitor(process,Pid), - Pid - end || Mod <- Mods], + Pid = cover:async_analyse_to_file(Mod,Opts), + erlang:monitor(process,Pid), + Pid + end || Mod <- Mods], get_downs(Pids,[]). get_downs([],Acc) -> Acc; get_downs(Pids,Acc) -> receive - {'DOWN', _Ref, _Type, Pid, A} -> - get_downs(lists:delete(Pid,Pids),[A|Acc]) + {'DOWN', _Ref, _Type, Pid, A} -> + get_downs(lists:delete(Pid,Pids),[A|Acc]) end. generate_modules(0,_,_,_) -> @@ -824,8 +817,8 @@ generate_modules(M,F,C,Dir) -> ModStr = "m" ++ integer_to_list(M), Mod = list_to_atom(ModStr), Src = ["-module(",ModStr,").\n" - "-compile(export_all).\n" | - generate_functions(F,C)], + "-compile(export_all).\n" | + generate_functions(F,C)], Erl = filename:join(Dir,ModStr++".erl"), ok = file:write_file(Erl,Src), {ok,Mod} = compile:file(Erl,[{outdir,Dir},debug_info,report]), @@ -846,143 +839,133 @@ generate_clauses(C,Func) -> generate_clauses(C-1,Func)]. -export_import(suite) -> []; export_import(Config) when is_list(Config) -> - ?line DataDir = ?config(data_dir, Config), - ?line ok = file:set_cwd(DataDir), - ?line PortCount = length(erlang:ports()), + DataDir = proplists:get_value(data_dir, Config), + ok = file:set_cwd(DataDir), + PortCount = length(erlang:ports()), %% Export one module - ?line {ok,f} = cover:compile(f), - ?line f:f1(), + {ok,f} = cover:compile(f), + f:f1(), %% check that no info is written about where data comes from when no %% files are imported - ?line ?t:capture_start(), - ?line check_f_calls(1,0), - ?line [] = ?t:capture_get(), - ?line ?t:capture_stop(), - ?line ok = cover:export("f_exported",f), - ?line check_f_calls(1,0), - ?line ok = cover:stop(), - + test_server:capture_start(), + check_f_calls(1,0), + [] = test_server:capture_get(), + test_server:capture_stop(), + ok = cover:export("f_exported",f), + check_f_calls(1,0), + ok = cover:stop(), + %% Check that same data exists after import and that info is written about %% data comming from imported file - ?line ok = cover:import("f_exported"), - ?line ?t:capture_start(), - ?line check_f_calls(1,0), - ?line [Text1] = ?t:capture_get(), - ?line "Analysis includes data from imported files"++_ = lists:flatten(Text1), - ?line ?t:capture_stop(), + ok = cover:import("f_exported"), + test_server:capture_start(), + check_f_calls(1,0), + [Text1] = test_server:capture_get(), + "Analysis includes data from imported files"++_ = lists:flatten(Text1), + test_server:capture_stop(), %% Export all modules - ?line {ok,a} = cover:compile(a), - ?line ?t:capture_start(), - ?line ok = cover:export("all_exported"), - ?line [] = ?t:capture_get(), -% ?line "Export includes data from imported files"++_ = lists:flatten(Text2), - ?line ?t:capture_stop(), - ?line ok = cover:stop(), - ?line ok = cover:import("all_exported"), - ?line check_f_calls(1,0), + {ok,a} = cover:compile(a), + test_server:capture_start(), + ok = cover:export("all_exported"), + [] = test_server:capture_get(), + % "Export includes data from imported files"++_ = lists:flatten(Text2), + test_server:capture_stop(), + ok = cover:stop(), + ok = cover:import("all_exported"), + check_f_calls(1,0), %% Check that data is reset when module is compiled again, and that %% warning is written when data is deleted for imported module. - ?line ?t:capture_start(), - ?line {ok,f} = cover:compile(f), - ?line timer:sleep(10), % capture needs some time - ?line [Text3] = ?t:capture_get(), - ?line "WARNING: Deleting data for module f imported from" ++ _ = - lists:flatten(Text3), - ?line ?t:capture_stop(), - ?line check_f_calls(0,0), - + test_server:capture_start(), + {ok,f} = cover:compile(f), + timer:sleep(10), % capture needs some time + [Text3] = test_server:capture_get(), + "WARNING: Deleting data for module f imported from" ++ _ = lists:flatten(Text3), + test_server:capture_stop(), + check_f_calls(0,0), + %% Check that data is summed up when first compiled and then imported %% The module which has been compiled (f) is loaded from the file %% all_exported again (since it has been reset during cover compiling), %% but the other module (a) is not loaded since it is already loaded - ?line f:f1(), - ?line f:f2(), - ?line ok = cover:import("f_exported"), - ?line ?t:capture_start(), - ?line ok = cover:import("all_exported"), - ?line [Text4] = ?t:capture_get(), % a is not loaded again - ?line "WARNING: Module a already imported from " ++ _ = lists:flatten(Text4), - ?line ?t:capture_stop(), - ?line check_f_calls(3,1), + f:f1(), + f:f2(), + ok = cover:import("f_exported"), + test_server:capture_start(), + ok = cover:import("all_exported"), + [Text4] = test_server:capture_get(), % a is not loaded again + "WARNING: Module a already imported from " ++ _ = lists:flatten(Text4), + test_server:capture_stop(), + check_f_calls(3,1), %% Check that warning is written when same file is imported twice, %% and that data is not imported again - ?line ?t:capture_start(), - ?line ok = cover:import("all_exported"), - ?line [Text5,Text6] = ?t:capture_get(), - ?line "WARNING: Module f already imported from " ++ _ = lists:flatten(Text5), - ?line "WARNING: Module a already imported from " ++ _ = lists:flatten(Text6), - ?line ?t:capture_stop(), - ?line check_f_calls(3,1), + test_server:capture_start(), + ok = cover:import("all_exported"), + [Text5,Text6] = test_server:capture_get(), + "WARNING: Module f already imported from " ++ _ = lists:flatten(Text5), + "WARNING: Module a already imported from " ++ _ = lists:flatten(Text6), + test_server:capture_stop(), + check_f_calls(3,1), %% Check that reset removes all data and that the file which has been %% reset can be imported again with no warning - ?line cover:reset(f), - ?line check_f_calls(0,0), - ?line ?t:capture_start(), - ?line ok = cover:import("all_exported"), - ?line [Text7] = ?t:capture_get(), % warning only on mod a - ?line "WARNING: Module a already imported from " ++ _ = lists:flatten(Text7), - ?line ?t:capture_stop(), - ?line check_f_calls(1,0), + cover:reset(f), + check_f_calls(0,0), + test_server:capture_start(), + ok = cover:import("all_exported"), + [Text7] = test_server:capture_get(), % warning only on mod a + "WARNING: Module a already imported from " ++ _ = lists:flatten(Text7), + test_server:capture_stop(), + check_f_calls(1,0), %% same as above - only reset all - ?line cover:reset(), - ?line check_f_calls(0,0), - ?line ?t:capture_start(), - ?line ok = cover:import("all_exported"), - ?line [] = ?t:capture_get(), % no warnings - ?line ?t:capture_stop(), - ?line check_f_calls(1,0), + cover:reset(), + check_f_calls(0,0), + test_server:capture_start(), + ok = cover:import("all_exported"), + [] = test_server:capture_get(), % no warnings + test_server:capture_stop(), + check_f_calls(1,0), %% Check no raw files are left open - ?line PortCount = length(erlang:ports()), + PortCount = length(erlang:ports()), %% Cleanup - ?line ok = cover:stop(), - ?line Files = lsfiles(), - ?line remove(["f_exported","all_exported"|files(Files, ".beam")]). + ok = cover:stop(), + Files = lsfiles(), + remove(["f_exported","all_exported"|files(Files, ".beam")]). -otp_5031(suite) -> []; otp_5031(Config) when is_list(Config) -> + ct:timetrap({seconds, 10}), - Dog = ?t:timetrap(?t:seconds(10)), - - {ok,N1} = ?t:start_node(cover_SUITE_otp_5031,slave,[]), - ?line {ok,[N1]} = cover:start(N1), - ?line {error,not_main_node} = rpc:call(N1,cover,modules,[]), - ?line cover:stop(), - ?t:stop_node(N1), - - ?t:timetrap_cancel(Dog), + {ok,N1} = test_server:start_node(cover_SUITE_otp_5031,slave,[]), + {ok,[N1]} = cover:start(N1), + {error,not_main_node} = rpc:call(N1,cover,modules,[]), + cover:stop(), + test_server:stop_node(N1), ok. -eif(doc) -> - ["Test the \'Exclude Included Functions\' functionality"]; -eif(suite) -> - []; +%% Test the \'Exclude Included Functions\' functionality eif(Config) when is_list(Config) -> - ?line ok = file:set_cwd(filename:join(?config(data_dir, Config), - "included_functions")), - ?line {ok, cover_inc} = compile:file(cover_inc,[debug_info]), - ?line {ok, cover_inc} = cover:compile_beam(cover_inc), + ok = file:set_cwd(filename:join(proplists:get_value(data_dir, Config), + "included_functions")), + {ok, cover_inc} = compile:file(cover_inc,[debug_info]), + {ok, cover_inc} = cover:compile_beam(cover_inc), %% This function will cause an included function to be executed. %% The analysis should only show the lines that actually exist %% in cover_inc.beam - not the ones from the included file. - ?line cover_inc:func(), - ?line {ok, [_, _]} = cover:analyse(cover_inc, line), + cover_inc:func(), + {ok, [_, _]} = cover:analyse(cover_inc, line), ok. - -otp_5305(suite) -> []; + otp_5305(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(priv_dir, Config)), + ok = file:set_cwd(proplists:get_value(priv_dir, Config)), File = "t.erl", Test = <<"-module(t). @@ -991,35 +974,32 @@ otp_5305(Config) when is_list(Config) -> t() -> ets:fun2ms(fun(X) -> X end). ">>, - ?line ok = file:write_file(File, Test), - ?line {ok, t} = cover:compile(File), - ?line ok = file:delete(File), - + ok = file:write_file(File, Test), + {ok, t} = cover:compile(File), + ok = file:delete(File), ok. -otp_5418(suite) -> []; otp_5418(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(priv_dir, Config)), + ok = file:set_cwd(proplists:get_value(priv_dir, Config)), File = "t.erl", Test = <<"-module(t). ">>, - ?line ok = file:write_file(File, Test), - ?line {ok, t} = cover:compile(File), - ?line {ok,{t,{0,0}}} = cover:analyse(t, module), - ?line ok = file:delete(File), - + ok = file:write_file(File, Test), + {ok, t} = cover:compile(File), + {ok,{t,{0,0}}} = cover:analyse(t, module), + ok = file:delete(File), ok. otp_6115(Config) when is_list(Config) -> - ?line {ok, CWD} = file:get_cwd(), - ?line Dir = filename:join(?config(data_dir, Config), otp_6115), - ?line ok = file:set_cwd(Dir), - ?line {ok, f1} = compile:file(f1, [debug_info]), - ?line {ok, f2} = compile:file(f2, [debug_info]), + {ok, CWD} = file:get_cwd(), + Dir = filename:join(proplists:get_value(data_dir, Config), otp_6115), + ok = file:set_cwd(Dir), + {ok, f1} = compile:file(f1, [debug_info]), + {ok, f2} = compile:file(f2, [debug_info]), %% Cover compile f1, but not f2 - ?line {ok, f1} = cover:compile(f1), + {ok, f1} = cover:compile(f1), %% If f1 is cover compiled, a process P is started with a %% reference to the fun created in start_fail/0, and cover:stop() is @@ -1033,39 +1013,37 @@ otp_6115(Config) when is_list(Config) -> Pid2 = f1:start_b(), %% Now stop cover - ?line cover:stop(), - + cover:stop(), + %% Ensure that f1 is loaded (and not cover compiled), and that %% both Pid1 and Pid2 are dead. case code:which(f1) of - Beam when is_list(Beam) -> - ok; - Other -> - ?line ?t:fail({"f1 is not reloaded", Other}) + Beam when is_list(Beam) -> + ok; + Other -> + ct:fail({"f1 is not reloaded", Other}) end, case process_info(Pid1) of - undefined -> - ok; - _PI1 -> - RefToOldP1 = erlang:check_process_code(Pid1, f1), - ?t:fail({"Pid1 still alive", RefToOldP1}) + undefined -> + ok; + _PI1 -> + RefToOldP1 = erlang:check_process_code(Pid1, f1), + ct:fail({"Pid1 still alive", RefToOldP1}) end, case process_info(Pid2) of - undefined -> - ok; - _PI2 -> - RefToOldP2 = erlang:check_process_code(Pid1, f2), - ?t:fail({"Pid2 still alive", RefToOldP2}) + undefined -> + ok; + _PI2 -> + RefToOldP2 = erlang:check_process_code(Pid1, f2), + ct:fail({"Pid2 still alive", RefToOldP2}) end, - ?line file:set_cwd(CWD), + file:set_cwd(CWD), ok. -otp_7095(doc) -> - ["andalso/orelse"]; -otp_7095(suite) -> []; +%% andalso/orelse otp_7095(Config) when is_list(Config) -> - ?line ok = file:set_cwd(?config(priv_dir, Config)), + ok = file:set_cwd(proplists:get_value(priv_dir, Config)), File = "t.erl", Test = <<"-module(t). @@ -1151,90 +1129,84 @@ otp_7095(Config) when is_list(Config) -> add_one(T) -> put(T, get(T) + 1). % 82 ">>, - ?line ok = file:write_file(File, Test), - ?line {ok, t} = cover:compile(File), - ?line ok = t:t(), - ?line {ok,[{{t,4},1},{{t,5},1},{{t,6},1},{{t,7},1},{{t,8},1},{{t,9},1}, - {{t,10},1},{{t,11},1},{{t,12},1},{{t,13},1},{{t,14},1}, - {{t,15},1},{{t,16},1},{{t,17},1}, - {{t,20},1},{{t,22},0}, - {{t,25},1},{{t,27},1}, - {{t,30},1},{{t,32},1}, - {{t,35},1},{{t,37},0}, - {{t,40},1},{{t,42},1},{{t,44},1}, - {{t,47},1},{{t,48},1}, - {{t,51},1},{{t,53},1},{{t,55},0}, - {{t,58},1},{{t,60},1},{{t,62},1},{{t,64},0}, - {{t,67},1},{{t,69},1},{{t,71},1},{{t,74},1}, - {{t,76},0},{{t,78},1}, - {{t,82},2}]} = cover:analyse(t, calls, line), - ?line ok = file:delete(File), - + ok = file:write_file(File, Test), + {ok, t} = cover:compile(File), + ok = t:t(), + {ok,[{{t,4},1},{{t,5},1},{{t,6},1},{{t,7},1},{{t,8},1},{{t,9},1}, + {{t,10},1},{{t,11},1},{{t,12},1},{{t,13},1},{{t,14},1}, + {{t,15},1},{{t,16},1},{{t,17},1}, + {{t,20},1},{{t,22},0}, + {{t,25},1},{{t,27},1}, + {{t,30},1},{{t,32},1}, + {{t,35},1},{{t,37},0}, + {{t,40},1},{{t,42},1},{{t,44},1}, + {{t,47},1},{{t,48},1}, + {{t,51},1},{{t,53},1},{{t,55},0}, + {{t,58},1},{{t,60},1},{{t,62},1},{{t,64},0}, + {{t,67},1},{{t,69},1},{{t,71},1},{{t,74},1}, + {{t,76},0},{{t,78},1}, + {{t,82},2}]} = cover:analyse(t, calls, line), + ok = file:delete(File), ok. -otp_8270(doc) -> - ["OTP-8270. Bug."]; -otp_8270(suite) -> []; +%% OTP-8270. Bug. otp_8270(Config) when is_list(Config) -> - ?line DataDir = ?config(data_dir, Config), - ?line ok = file:set_cwd(DataDir), + DataDir = proplists:get_value(data_dir, Config), + ok = file:set_cwd(DataDir), - ?line PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), As = [{args," -pa " ++ PrivDir}], - ?line {ok,N1} = ?t:start_node(cover_n1,slave,As), - ?line {ok,N2} = ?t:start_node(cover_n2,slave,As), - ?line {ok,N3} = ?t:start_node(cover_n3,slave,As), - + {ok,N1} = test_server:start_node(cover_n1,slave,As), + {ok,N2} = test_server:start_node(cover_n2,slave,As), + {ok,N3} = test_server:start_node(cover_n3,slave,As), + timer:sleep(500), {ok,[_,_,_]} = cover:start(nodes()), - Test = << - "-module(m).\n" - "-compile(export_all).\n" - "t() -> t(0).\n" - "l() ->\n" - " catch ets:tab2list(cover_internal_data_table).\n" - "t(Sz) ->\n" - " case ets:info(cover_internal_data_table, size) of\n" - " Sz ->\n" - " m:t(Sz); % Not a local call! Newly loaded code is entered.\n" - " NSz ->\n" - " % error_logger:info_msg(\"~p: ~p ~p change~n L1 ~p~n\", \n" - " % [node(), Sz, NSz, l()]),\n" - " m:t(NSz)\n" - " end.\n">>, - ?line _File = c_mod(m, Test, Config), + Test = <<"-module(m).\n" + "-compile(export_all).\n" + "t() -> t(0).\n" + "l() ->\n" + " catch ets:tab2list(cover_internal_data_table).\n" + "t(Sz) ->\n" + " case ets:info(cover_internal_data_table, size) of\n" + " Sz ->\n" + " m:t(Sz); % Not a local call! Newly loaded code is entered.\n" + " NSz ->\n" + " % error_logger:info_msg(\"~p: ~p ~p change~n L1 ~p~n\", \n" + " % [node(), Sz, NSz, l()]),\n" + " m:t(NSz)\n" + " end.\n">>, + _File = c_mod(m, Test, Config), Fun = fun m:t/0, - ?line Pid1 = spawn(Fun), - ?line Pid2 = spawn(N1, Fun), - ?line Pid3 = spawn(N2, Fun), - ?line Pid4 = spawn(N3, Fun), + Pid1 = spawn(Fun), + Pid2 = spawn(N1, Fun), + Pid3 = spawn(N2, Fun), + Pid4 = spawn(N3, Fun), - ?line {ok, m} = cover:compile_beam(m), + {ok, m} = cover:compile_beam(m), timer:sleep(1000), - ?line Info = erlang:process_info(Pid1), - ?line N1_info = rpc:call(N1, erlang, process_info, [Pid2]), - ?line N2_info = rpc:call(N2, erlang, process_info, [Pid3]), - ?line N3_info = rpc:call(N3, erlang, process_info, [Pid4]), + Info = erlang:process_info(Pid1), + N1_info = rpc:call(N1, erlang, process_info, [Pid2]), + N2_info = rpc:call(N2, erlang, process_info, [Pid3]), + N3_info = rpc:call(N3, erlang, process_info, [Pid4]), - ?line true = is_list(Info), - ?line {N1,true} = {N1,is_list(N1_info)}, - ?line {N2,true} = {N2,is_list(N2_info)}, - ?line {N3,true} = {N3,is_list(N3_info)}, + true = is_list(Info), + {N1,true} = {N1,is_list(N1_info)}, + {N2,true} = {N2,is_list(N2_info)}, + {N3,true} = {N3,is_list(N3_info)}, exit(Pid1,kill), - ?line ?t:stop_node(N1), - ?line ?t:stop_node(N2), - ?line ?t:stop_node(N3), + test_server:stop_node(N1), + test_server:stop_node(N2), + test_server:stop_node(N3), ok. -otp_8273(doc) -> - ["OTP-8273. Bug."]; -otp_8273(suite) -> []; +%% OTP-8273. Bug. otp_8273(Config) when is_list(Config) -> Test = <<"-module(t). -export([t/0]). @@ -1243,27 +1215,22 @@ otp_8273(Config) when is_list(Config) -> bar = false orelse bar, ok. ">>, - ?line File = cc_mod(t, Test, Config), - ?line ok = t:t(), - ?line ok = file:delete(File), + File = cc_mod(t, Test, Config), + ok = t:t(), + ok = file:delete(File), ok. -otp_8340(doc) -> - ["OTP-8340. Bug."]; -otp_8340(suite) -> []; +%% OTP-8340. Bug. otp_8340(Config) when is_list(Config) -> [{{t,1},1},{{t,2},1},{{t,4},1}] = - analyse_expr(<<"<< \n" - " <<3:2, \n" - " SeqId:62>> \n" - " || SeqId <- [64] >>">>, Config), - + analyse_expr(<<"<< \n" + " <<3:2, \n" + " SeqId:62>> \n" + " || SeqId <- [64] >>">>, Config), ok. -otp_8188(doc) -> - ["Clauses on the same line."]; -otp_8188(suite) -> []; +%% Clauses on the same line. otp_8188(Config) when is_list(Config) -> %% This example covers the bug report: Test = <<"-module(t). @@ -1279,10 +1246,10 @@ otp_8188(Config) when is_list(Config) -> _Res = ?FOOBAR(X). ">>, - ?line File = cc_mod(t, Test, Config), - ?line false = t:test(nok), - ?line {ok,[{{t,11},1},{{t,12},1}]} = cover:analyse(t, calls, line), - ?line ok = file:delete(File), + File = cc_mod(t, Test, Config), + false = t:test(nok), + {ok,[{{t,11},1},{{t,12},1}]} = cover:analyse(t, calls, line), + ok = file:delete(File), %% Bit string comprehensions are now traversed; %% the handling of list comprehensions has been improved: @@ -1293,39 +1260,39 @@ otp_8188(Config) when is_list(Config) -> ok. bug_8188(Cf) -> - ?line [{{t,1},1},{{t,2},1},{{t,3},1}] = - analyse_expr(<<"A = 3,\n" % 1 - " case A of\n" % 1 - " 2 -> two; 3 -> three end, A + 2">>, % 1 - Cf), - - ?line [{{t,1},1}, - {{t,2},0}, - {{t,3},1}, - {{t,4},1}, - {{t,5},1}, - {{t,6},0}, - {{t,7},1}, - {{t,9},2}] = - analyse_expr(<<"case two() of\n" % 1 - " 1 -> 2;\n" % 0 - " _ -> begin 3 end\n" % 1 - " +\n" % 1 - " begin 4 end end, case two() of\n" % 1 - " 1 -> a;\n" % 0 - " 2 -> b; 3 -> c\n" % 1 - " end.\n" - "two() -> 2">>, Cf), % 2 - - ?line [{{t,1},1}, {{t,2},1}, {{t,3},1}, - {{t,4},1}, {{t,5},1}, {{t,6},0}] = - analyse_expr(<<" self() ! 1,\n" - " receive \n" - " X=1 -> a;\n" - " X=2 -> b end, case X of \n" - " 1 -> a;\n" - " 2 -> b\n" - " end">>, Cf), + [{{t,1},1},{{t,2},1},{{t,3},1}] = + analyse_expr(<<"A = 3,\n" % 1 + " case A of\n" % 1 + " 2 -> two; 3 -> three end, A + 2">>, % 1 + Cf), + + [{{t,1},1}, + {{t,2},0}, + {{t,3},1}, + {{t,4},1}, + {{t,5},1}, + {{t,6},0}, + {{t,7},1}, + {{t,9},2}] = + analyse_expr(<<"case two() of\n" % 1 + " 1 -> 2;\n" % 0 + " _ -> begin 3 end\n" % 1 + " +\n" % 1 + " begin 4 end end, case two() of\n" % 1 + " 1 -> a;\n" % 0 + " 2 -> b; 3 -> c\n" % 1 + " end.\n" + "two() -> 2">>, Cf), % 2 + + [{{t,1},1}, {{t,2},1}, {{t,3},1}, + {{t,4},1}, {{t,5},1}, {{t,6},0}] = + analyse_expr(<<" self() ! 1,\n" + " receive \n" + " X=1 -> a;\n" + " X=2 -> b end, case X of \n" + " 1 -> a;\n" + " 2 -> b\n" + " end">>, Cf), T0 = <<"t1(X) ->\n " "case X of\n" @@ -1339,42 +1306,42 @@ bug_8188(Cf) -> " end">>, T1 = [<<"a = t1(1). ">>,T0], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},0}, - {{t,5},0}, {{t,6},1}, {{t,7},1}, {{t,8},0}, {{t,9},0}] = - analyse_expr(T1, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},0}, + {{t,5},0}, {{t,6},1}, {{t,7},1}, {{t,8},0}, {{t,9},0}] = + analyse_expr(T1, Cf), T2 = [<<"b = t1(2). ">>,T0], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}, {{t,9},0}] = - analyse_expr(T2, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}, {{t,9},0}] = + analyse_expr(T2, Cf), T3 = [<<"c = t1(3). ">>,T0], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},1}, {{t,6},1}, {{t,7},0}, {{t,8},1}, {{t,9},0}] = - analyse_expr(T3, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},1}, {{t,6},1}, {{t,7},0}, {{t,8},1}, {{t,9},0}] = + analyse_expr(T3, Cf), T4 = [<<"d = t1(4). ">>,T0], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},0}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},0}, {{t,9},1}] = - analyse_expr(T4, Cf), - - ?line [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},1},{{t,5},1}] = - analyse_expr( - <<"2 = x3(1). " - "x3(X) ->\n" - " case X of \n" - " 1 -> case X of\n" - " 1 -> a, Y = 2;\n" - " 2 -> b, Y = 3 end, Y; 2 -> Y = 4 end, Y">>, Cf), - - ?line [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},1}] = - analyse_expr( - <<"1 = x4(1). " - "x4(X) ->\n" - " case X of\n" - " 1 -> case X of\n" - " 1 -> Y = 1 end, case X of 1 -> Y = 1 end, Y end">>, - Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},0}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},0}, {{t,9},1}] = + analyse_expr(T4, Cf), + + [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},1},{{t,5},1}] = + analyse_expr( + <<"2 = x3(1). " + "x3(X) ->\n" + " case X of \n" + " 1 -> case X of\n" + " 1 -> a, Y = 2;\n" + " 2 -> b, Y = 3 end, Y; 2 -> Y = 4 end, Y">>, Cf), + + [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},1}] = + analyse_expr( + <<"1 = x4(1). " + "x4(X) ->\n" + " case X of\n" + " 1 -> case X of\n" + " 1 -> Y = 1 end, case X of 1 -> Y = 1 end, Y end">>, + Cf), T10 = <<"t1(X) ->\n" "if\n" @@ -1386,19 +1353,16 @@ bug_8188(Cf) -> " 2 -> b; 3 -> c\n" " end">>, T11 = [<<"a = t1(1). ">>,T10], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},1}, - {{t,5},1}, {{t,6},1}, {{t,7},1}, {{t,8},0}] = - analyse_expr(T11, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},1}, + {{t,5},1}, {{t,6},1}, {{t,7},1}, {{t,8},0}] = analyse_expr(T11, Cf), T12 = [<<"b = t1(2). ">>,T10], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = - analyse_expr(T12, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = analyse_expr(T12, Cf), T13 = [<<"c = t1(3). ">>,T10], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = - analyse_expr(T13, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = analyse_expr(T13, Cf), T20 = <<"t1(X) ->\n" "case X of\n" @@ -1411,204 +1375,185 @@ bug_8188(Cf) -> " end">>, T21 = [<<"a = t1(1). ">>,T20], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},0}, - {{t,5},0}, {{t,6},1}, {{t,7},1}, {{t,8},0}] = - analyse_expr(T21, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},1}, {{t,4},0}, + {{t,5},0}, {{t,6},1}, {{t,7},1}, {{t,8},0}] = analyse_expr(T21, Cf), T22 = [<<"b = t1(2). ">>,T20], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = - analyse_expr(T22, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = analyse_expr(T22, Cf), T23 = [<<"c = t1(3). ">>,T20], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, - {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = - analyse_expr(T23, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, {{t,4},1}, + {{t,5},0}, {{t,6},1}, {{t,7},0}, {{t,8},1}] = analyse_expr(T23, Cf), T30 = << - "t1(X) ->\n" - "case X of\n" - " 1 -> a;\n" - " 2 -> b; 3 -> case X of 1 -> a; 2 -> b; 3 -> c end end, case X of\n" - " 1 -> a;\n" - " 2 -> b; 3 -> c\n" - " end\n">>, + "t1(X) ->\n" + "case X of\n" + " 1 -> a;\n" + " 2 -> b; 3 -> case X of 1 -> a; 2 -> b; 3 -> c end end, case X of\n" + " 1 -> a;\n" + " 2 -> b; 3 -> c\n" + " end\n">>, T31 = [<<"a = t1(1). ">>,T30], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},1}, - {{t,4},1}, {{t,5},1}, {{t,6},0}] = - analyse_expr(T31, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},1}, + {{t,4},1}, {{t,5},1}, {{t,6},0}] = analyse_expr(T31, Cf), T32 = [<<"b = t1(2). ">>,T30], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, - {{t,4},1}, {{t,5},0}, {{t,6},1}] = - analyse_expr(T32, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, + {{t,4},1}, {{t,5},0}, {{t,6},1}] = analyse_expr(T32, Cf), T33 = [<<"c = t1(3). ">>,T30], - ?line [{{t,1},1}, {{t,2},1}, {{t,3},0}, - {{t,4},1}, {{t,5},0}, {{t,6},1}] = - analyse_expr(T33, Cf), + [{{t,1},1}, {{t,2},1}, {{t,3},0}, + {{t,4},1}, {{t,5},0}, {{t,6},1}] = analyse_expr(T33, Cf), %% 'try' now traverses the body as a body... - ?line [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},0},{{t,6},1}] = - analyse_expr(<<"try \n" - " B = 2, \n" - " C = erlang:error(foo), \n" - " {B,C} \n" - "catch _:_ -> \n" - " foo \n" - "end">>, Cf), + [{{t,1},1},{{t,2},1},{{t,3},1},{{t,4},0},{{t,6},1}] = + analyse_expr(<<"try \n" + " B = 2, \n" + " C = erlang:error(foo), \n" + " {B,C} \n" + "catch _:_ -> \n" + " foo \n" + "end">>, Cf), %% receive after: - ?line [{{t,1},1},{{t,2},0},{{t,3},1}] = - analyse_expr(<<"receive \n" - " X=1 -> a; \n" - " X=2 -> b after begin 10 end -> X=3 end">>, Cf), - ?line [{{t,1},1},{{t,2},0},{{t,3},1}] = - analyse_expr(<<"receive \n" - " X=1 -> a; \n" - " X=2 -> b after 10 -> begin X=3 end end">>, Cf), + [{{t,1},1},{{t,2},0},{{t,3},1}] = + analyse_expr(<<"receive \n" + " X=1 -> a; \n" + " X=2 -> b after begin 10 end -> X=3 end">>, Cf), + [{{t,1},1},{{t,2},0},{{t,3},1}] = + analyse_expr(<<"receive \n" + " X=1 -> a; \n" + " X=2 -> b after 10 -> begin X=3 end end">>, Cf), ok. comprehension_8188(Cf) -> - ?line [{{t,1},1}] = - analyse_expr(<<"[begin X end || X <- [1,2,3], X > 1]">>, Cf), - ?line [{{t,1},1},{{t,2},1}] = - analyse_expr(<<"[begin X end || \n" - " X <- [1,2,3], X > 1]">>, Cf), - ?line [{{t,1},1},{{t,2},1},{{t,3},3}] = - analyse_expr(<<"[begin X end || \n " - " X <- [1,2,3], \n " - " X > 1]">>, Cf), - ?line [{{t,1},1},{{t,3},1},{{t,4},3}] = - analyse_expr(<<"[begin X end || \n " - " X <- \n " - " [1,2,3], \n " - " X > 1]">>, Cf), - ?line [{{t,1},1},{{t,2},2}] = - analyse_expr(<<"[ \n " - " X || X <- [1,2,3], X > 1]">>, Cf), - ?line [{{t,1},1},{{t,2},2},{{t,3},3}] = - analyse_expr(<<"[ \n" - " X || X <- [1,2,3], \n" - " X > 1]">>, Cf), - ?line [{{t,1},1},{{t,2},1},{{t,3},2}] = - analyse_expr(<<"[ \n " - " X || X <- [1,2,3], X > 1, \n" - " X > 2]">>, Cf), - - ?line [{{t,1},1}, - {{t,3},2}, - {{t,5},1}, - {{t,7},1}, - {{t,8},0}, - {{t,12},3}, - {{t,15},2}, - {{t,17},2}, - {{t,18},1}] = - analyse_expr(<<"[ \n" % 1 - " begin\n" - " X * 2\n" % 2 - " end ||\n" - " X <- [1,\n" % 1 - " case two() of\n" - " 2 -> 2;\n" % 1 - " _ -> two\n" % 0 - " end,\n" - " 3],\n" - " begin\n" - " math:sqrt(X) > 1.0\n" % 3 - " end,\n" - " begin\n" - " true\n" % 2 - " end,\n" - " true]. \n" % 2 - " two() -> 2">>, Cf), % 1 - - ?line [{{t,1},1}, - {{t,2},2}, - {{t,3},1}, - {{t,5},1}, - {{t,6},0}, - {{t,9},3}, - {{t,10},2}, - {{t,11},2}, - {{t,12},1}] = - analyse_expr(<<"[ \n" - " X * 2 || \n" % 2 - " X <- [1,\n" % 1 - " case two() of\n" - " 2 -> 2;\n" % 1 - " _ -> two\n" % 0 - " end,\n" - " 3],\n" - " math:sqrt(X) > 1.0,\n" % 3 - " true,\n" % 2 - " true]. \n" % 2 - " two() -> 2">>, Cf), % 1 - - ?line [{{t,1},1}, - {{t,2},2}, - {{t,3},1}, - {{t,4},1}, - {{t,5},0}, - {{t,8},1}, - {{t,9},0}, - {{t,12},3}, - {{t,13},2}, - {{t,14},2}] = - analyse_expr(<<"<< \n" % 1 - " << (X*2) >> || \n" % 2 - " <<X>> <= << (case two() of\n" - " 2 -> 1;\n" % 1 - " _ -> 2\n" % 0 - " end)/integer,\n" - " (case two() of \n" - " 2 -> 2;\n" % 1 - " _ -> two\n" % 0 - " end)/integer,\n" - " 3 >>, \n" - " math:sqrt(X) > 1.0,\n" % 3 - " true >>.\n" % 2 - "two() -> 2">>, Cf), - - ?line [{{t,1},1}, - {{t,2},4}, - {{t,4},1}, - {{t,6},1}, - {{t,7},0}, - {{t,10},3}, - {{t,11},2}, - {{t,12},4}, - {{t,13},1}] = - analyse_expr(<<"<< \n" % 1 - " << (2)\n" % 4 - " :(8) >> || \n" - " <<X>> <= << 1,\n" % 1 - " (case two() of \n" - " 2 -> 2;\n" % 1 - " _ -> two\n" % 0 - " end)/integer,\n" - " 3 >>, \n" - " math:sqrt(X) > 1.0,\n" % 3 - " <<_>> <= << 1, 2 >>,\n" % 2 - " true >>.\n" % 4 - "two() -> 2">>, Cf), % 1 - + [{{t,1},1}] = analyse_expr(<<"[begin X end || X <- [1,2,3], X > 1]">>, Cf), + [{{t,1},1},{{t,2},1}] = analyse_expr(<<"[begin X end || \n" + " X <- [1,2,3], X > 1]">>, Cf), + [{{t,1},1},{{t,2},1},{{t,3},3}] = analyse_expr(<<"[begin X end || \n " + " X <- [1,2,3], \n " + " X > 1]">>, Cf), + [{{t,1},1},{{t,3},1},{{t,4},3}] = analyse_expr(<<"[begin X end || \n " + " X <- \n " + " [1,2,3], \n " + " X > 1]">>, Cf), + [{{t,1},1},{{t,2},2}] = analyse_expr(<<"[ \n " + " X || X <- [1,2,3], X > 1]">>, Cf), + [{{t,1},1},{{t,2},2},{{t,3},3}] = analyse_expr(<<"[ \n" + " X || X <- [1,2,3], \n" + " X > 1]">>, Cf), + [{{t,1},1},{{t,2},1},{{t,3},2}] = analyse_expr(<<"[ \n " + " X || X <- [1,2,3], X > 1, \n" + " X > 2]">>, Cf), + + [{{t,1},1}, + {{t,3},2}, + {{t,5},1}, + {{t,7},1}, + {{t,8},0}, + {{t,12},3}, + {{t,15},2}, + {{t,17},2}, + {{t,18},1}] = analyse_expr(<<"[ \n" % 1 + " begin\n" + " X * 2\n" % 2 + " end ||\n" + " X <- [1,\n" % 1 + " case two() of\n" + " 2 -> 2;\n" % 1 + " _ -> two\n" % 0 + " end,\n" + " 3],\n" + " begin\n" + " math:sqrt(X) > 1.0\n" % 3 + " end,\n" + " begin\n" + " true\n" % 2 + " end,\n" + " true]. \n" % 2 + " two() -> 2">>, Cf), % 1 + + [{{t,1},1}, + {{t,2},2}, + {{t,3},1}, + {{t,5},1}, + {{t,6},0}, + {{t,9},3}, + {{t,10},2}, + {{t,11},2}, + {{t,12},1}] = analyse_expr(<<"[ \n" + " X * 2 || \n" % 2 + " X <- [1,\n" % 1 + " case two() of\n" + " 2 -> 2;\n" % 1 + " _ -> two\n" % 0 + " end,\n" + " 3],\n" + " math:sqrt(X) > 1.0,\n" % 3 + " true,\n" % 2 + " true]. \n" % 2 + " two() -> 2">>, Cf), % 1 + + [{{t,1},1}, + {{t,2},2}, + {{t,3},1}, + {{t,4},1}, + {{t,5},0}, + {{t,8},1}, + {{t,9},0}, + {{t,12},3}, + {{t,13},2}, + {{t,14},2}] = analyse_expr(<<"<< \n" % 1 + " << (X*2) >> || \n" % 2 + " <<X>> <= << (case two() of\n" + " 2 -> 1;\n" % 1 + " _ -> 2\n" % 0 + " end)/integer,\n" + " (case two() of \n" + " 2 -> 2;\n" % 1 + " _ -> two\n" % 0 + " end)/integer,\n" + " 3 >>, \n" + " math:sqrt(X) > 1.0,\n" % 3 + " true >>.\n" % 2 + "two() -> 2">>, Cf), + [{{t,1},1}, + {{t,2},4}, + {{t,4},1}, + {{t,6},1}, + {{t,7},0}, + {{t,10},3}, + {{t,11},2}, + {{t,12},4}, + {{t,13},1}] = analyse_expr(<<"<< \n" % 1 + " << (2)\n" % 4 + " :(8) >> || \n" + " <<X>> <= << 1,\n" % 1 + " (case two() of \n" + " 2 -> 2;\n" % 1 + " _ -> two\n" % 0 + " end)/integer,\n" + " 3 >>, \n" + " math:sqrt(X) > 1.0,\n" % 3 + " <<_>> <= << 1, 2 >>,\n" % 2 + " true >>.\n" % 4 + "two() -> 2">>, Cf), % 1 ok. eep37(Config) when is_list(Config) -> [{{t,1},1},{{t,2},1},{{t,4},6},{{t,6},1},{{t,8},1}] = - analyse_expr(<<"begin\n" % 1 - " F =\n" % 1 - " fun Fact(N) when N > 0 ->\n" - " N * Fact(N - 1);\n" % 6 - " Fact(0) ->\n" - " 1\n" % 1 - " end,\n" - " F(6)\n" % 1 - "end\n">>, - Config), + analyse_expr(<<"begin\n" % 1 + " F =\n" % 1 + " fun Fact(N) when N > 0 ->\n" + " N * Fact(N - 1);\n" % 6 + " Fact(0) ->\n" + " 1\n" % 1 + " end,\n" + " F(6)\n" % 1 + "end\n">>, + Config), ok. otp_10979_hanging_node(_Config) -> @@ -1621,42 +1566,40 @@ otp_10979_hanging_node(_Config) -> P2 = processes(), case P2--P1 of - [] -> - ok; - New -> - [io:format("New: ~p, ~p~n",[P,process_info(P)]) || P<-New], - ct:fail(hanging_process) + [] -> + ok; + New -> + [io:format("New: ~p, ~p~n",[P,process_info(P)]) || P<-New], + ct:fail(hanging_process) end, ok. -compile_beam_opts(doc) -> - ["Take compiler options from beam in cover:compile_beam"]; -compile_beam_opts(suite) -> []; +%% Take compiler options from beam in cover:compile_beam compile_beam_opts(Config) when is_list(Config) -> {ok, Cwd} = file:get_cwd(), - ok = file:set_cwd(?config(priv_dir, Config)), - IncDir = filename:join(?config(data_dir, Config), - "included_functions"), - File = filename:join([?config(data_dir, Config), "otp_11439", "t.erl"]), + ok = file:set_cwd(proplists:get_value(priv_dir, Config)), + IncDir = filename:join(proplists:get_value(data_dir, Config), + "included_functions"), + File = filename:join([proplists:get_value(data_dir, Config), "otp_11439", "t.erl"]), %% use all compiler options allowed by cover:filter_options %% i and d don't make sense when compiling from beam though {ok, t} = - compile:file(File, [{i, IncDir}, - {d, 'BOOL'}, - {d, 'MACRO', macro_defined}, - export_all, - debug_info, - return_errors]), + compile:file(File, [{i, IncDir}, + {d, 'BOOL'}, + {d, 'MACRO', macro_defined}, + export_all, + debug_info, + return_errors]), code:purge(t), code:delete(t), Exports = - [{func1,0}, - {macro, 0}, - {exported,0}, - {nonexported,0}, - {module_info,0}, - {module_info,1}], + [{func1,0}, + {macro, 0}, + {exported,0}, + {nonexported,0}, + {module_info,0}, + {module_info,1}], Exports = t:module_info(exports), {ok, t} = cover:compile_beam("t"), Exports = t:module_info(exports), @@ -1664,12 +1607,10 @@ compile_beam_opts(Config) when is_list(Config) -> ok = file:set_cwd(Cwd), ok. -analyse_no_beam(doc) -> - ["Don't crash if beam is not available"]; -analyse_no_beam(suite) -> []; +%% Don't crash if beam is not available analyse_no_beam(Config) when is_list(Config) -> {ok, Cwd} = file:get_cwd(), - ok = file:set_cwd(?config(data_dir, Config)), + ok = file:set_cwd(proplists:get_value(data_dir, Config)), code:purge(t), code:delete(t), @@ -1707,8 +1648,8 @@ analyse_no_beam(Config) when is_list(Config) -> %% file in this situation. The test below tests that this bug is %% corrected. line_0(Config) -> - ok = file:set_cwd(filename:join(?config(data_dir, Config), - "include_eunit_hrl")), + ok = file:set_cwd(filename:join(proplists:get_value(data_dir, Config), + "include_eunit_hrl")), {ok, cover_inc_eunit} = compile:file(cover_inc_eunit,[debug_info]), {ok, cover_inc_eunit} = cover:compile_beam(cover_inc_eunit), {ok, CovOut} = cover:analyse_to_file(cover_inc_eunit), @@ -1723,14 +1664,14 @@ line_0(Config) -> %% OTP-13200: Return error instead of crashing when trying to compile %% a beam which has no 'file' attribute. compile_beam_no_file(Config) -> - PrivDir = ?config(priv_dir,Config), + PrivDir = proplists:get_value(priv_dir,Config), Dir = filename:join(PrivDir,"compile_beam_no_file"), ok = filelib:ensure_dir(filename:join(Dir,"*")), code:add_patha(Dir), Str = lists:concat( - ["-module(nofile).\n" - "-compile(export_all).\n" - "foo() -> ok.\n"]), + ["-module(nofile).\n" + "-compile(export_all).\n" + "foo() -> ok.\n"]), TT = do_scan(Str), Forms = [ begin {ok,Y} = erl_parse:parse_form(X),Y end || X <- TT ], {ok,_,Bin} = compile:forms(Forms,[debug_info]), @@ -1746,8 +1687,7 @@ do_scan(Str) -> {done,{ok,T,_},C} = erl_scan:tokens([],Str,0), [ T | do_scan(C) ]. -otp_13277(doc) -> - ["PR 856. Fix a bc bug."]; +%% PR 856. Fix a bc bug. otp_13277(Config) -> Test = <<"-module(t). -export([t/0]). @@ -1759,9 +1699,9 @@ otp_13277(Config) -> t() -> pad(<<\"hi\">>, 2). ">>, - ?line File = cc_mod(t, Test, Config), - ?line <<"hi##">> = t:t(), - ?line ok = file:delete(File), + File = cc_mod(t, Test, Config), + <<"hi##">> = t:t(), + ok = file:delete(File), ok. %% Test general expressions in a binary comprehension. @@ -1793,7 +1733,7 @@ analyse_expr(Expr, Config) -> cc_mod(M, Binary, Config) -> {ok, Dir} = file:get_cwd(), - PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), ok = file:set_cwd(PrivDir), File = atom_to_list(M) ++ ".erl", try @@ -1805,7 +1745,7 @@ cc_mod(M, Binary, Config) -> c_mod(M, Binary, Config) -> {ok, Dir} = file:get_cwd(), - PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), ok = file:set_cwd(PrivDir), File = atom_to_list(M) ++ ".erl", try @@ -1828,12 +1768,12 @@ lsfiles(Dir) -> files(Files, Ext) -> lists:filter(fun(File) -> - case filename:extension(File) of - Ext -> true; - _ -> false - end - end, - Files). + case filename:extension(File) of + Ext -> true; + _ -> false + end + end, + Files). remove([File|Files]) -> ok = file:delete(File), @@ -1850,9 +1790,9 @@ decompile([]) -> is_unloaded(What) -> if - is_list(What) -> true; - What==non_existing -> true; - true -> false + is_list(What) -> true; + What==non_existing -> true; + true -> false end. check_f_calls(F1,F2) -> @@ -1862,18 +1802,18 @@ check_f_calls(F1,F2) -> cover_which_nodes(Expected) -> case cover:which_nodes() of - Expected -> - ok; - Other -> - {Time,ok} = timer:tc(fun Retry() -> - case cover:which_nodes() of - Expected -> ok; - _ -> - ?t:sleep(100), - Retry() - end - end), - io:format("~p ms before cover:which_nodes() returned ~p", - [Time,Expected]), - Expected = Other + Expected -> + ok; + Other -> + {Time,ok} = timer:tc(fun Retry() -> + case cover:which_nodes() of + Expected -> ok; + _ -> + timer:sleep(100), + Retry() + end + end), + io:format("~p ms before cover:which_nodes() returned ~p", + [Time,Expected]), + Expected = Other end. diff --git a/lib/tools/test/cprof_SUITE.erl b/lib/tools/test/cprof_SUITE.erl index 8beaf4f399..9cbc27fb17 100644 --- a/lib/tools/test/cprof_SUITE.erl +++ b/lib/tools/test/cprof_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2002-2013. All Rights Reserved. +%% Copyright Ericsson AB 2002-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -44,7 +44,7 @@ -else. -include_lib("common_test/include/ct.hrl"). -endif. - + -ifdef(debug). -ifdef(STANDALONE). -define(line, erlang:display({?MODULE,?LINE}), ). @@ -56,7 +56,7 @@ -endif. -define(dbgformat(A,B),noop). -endif. - + -ifdef(STANDALONE). config(priv_dir, _) -> "."; @@ -64,69 +64,43 @@ config(data_dir, _) -> "cprof_SUITE_data". -else. %% When run in test server. --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2, - init_per_testcase/2, end_per_testcase/2, - not_run/1]). +-export([all/0, suite/0, + init_per_testcase/2, end_per_testcase/2, + not_run/1]). -export([basic/1, on_load/1, modules/1]). - + init_per_testcase(_Case, Config) -> - ?line Dog=test_server:timetrap(test_server:seconds(30)), - [{watchdog, Dog}|Config]. + Config. -end_per_testcase(_Case, Config) -> +end_per_testcase(_Case, _Config) -> erlang:trace_pattern({'_','_','_'}, false, [local,meta,call_count]), erlang:trace_pattern(on_load, false, [local,meta,call_count]), erlang:trace(all, false, [all]), - Dog=?config(watchdog, Config), - test_server:timetrap_cancel(Dog), ok. -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{seconds,30}}]. all() -> case test_server:is_native(cprof_SUITE) of - true -> [not_run]; - false -> [basic, on_load, modules] + true -> [not_run]; + false -> [basic, on_load, modules] end. -groups() -> - []. - -init_per_suite(Config) -> - Config. - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - not_run(Config) when is_list(Config) -> {skipped,"Native code"}. -basic(suite) -> - []; -basic(doc) -> - ["Tests basic profiling"]; +%% Tests basic profiling basic(Config) when is_list(Config) -> basic_test(). -on_load(suite) -> - []; -on_load(doc) -> - ["Tests profiling of unloaded module"]; +%% Tests profiling of unloaded module on_load(Config) when is_list(Config) -> on_load_test(Config). -modules(suite) -> - []; -modules(doc) -> - ["Tests profiling of several modules"]; +%% Tests profiling of several modules modules(Config) when is_list(Config) -> modules_test(Config). @@ -137,164 +111,163 @@ modules(Config) when is_list(Config) -> %%% basic_test() -> - ?line M = 1000, + M = 1000, %% - ?line M2 = M*2, - ?line M3 = M*3, - ?line M2__1 = M2 + 1, - ?line M3__1 = M3 + 1, - ?line N = cprof:stop(), + M2 = M*2, + M3 = M*3, + M2__1 = M2 + 1, + M3__1 = M3 + 1, + N = cprof:stop(), %% - ?line 2 = cprof:start(?MODULE, seq_r), - ?line 1 = cprof:start(?MODULE, seq, 3), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), - ?line L = lists:reverse(Lr), + 2 = cprof:start(?MODULE, seq_r), + 1 = cprof:start(?MODULE, seq, 3), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), + L = lists:reverse(Lr), %% - ?line io:format("~p~n~p~n~p~n", - [erlang:trace_info({?MODULE,sec_r,3}, all), - erlang:trace_info({?MODULE,sec_r,4}, all), - erlang:trace_info({?MODULE,sec,3}, all)]), + io:format("~p~n~p~n~p~n", + [erlang:trace_info({?MODULE,sec_r,3}, all), + erlang:trace_info({?MODULE,sec_r,4}, all), + erlang:trace_info({?MODULE,sec,3}, all)]), %% - ?line ModAna1 = {?MODULE,M2__1,[{{?MODULE,seq_r,4},M}, - {{?MODULE,seq,3},M}, - {{?MODULE,seq_r,3},1}]}, - ?line ModAna1 = cprof:analyse(?MODULE,0), - ?line {M2__1, [ModAna1]} = cprof:analyse(), - ?line ModAna1 = cprof:analyse(?MODULE, 1), - ?line {M2__1, [ModAna1]} = cprof:analyse(1), + ModAna1 = {?MODULE,M2__1,[{{?MODULE,seq_r,4},M}, + {{?MODULE,seq,3},M}, + {{?MODULE,seq_r,3},1}]}, + ModAna1 = cprof:analyse(?MODULE,0), + {M2__1, [ModAna1]} = cprof:analyse(), + ModAna1 = cprof:analyse(?MODULE, 1), + {M2__1, [ModAna1]} = cprof:analyse(1), %% - ?line ModAna2 = {?MODULE,M2__1,[{{?MODULE,seq_r,4},M}, - {{?MODULE,seq,3},M}]}, - ?line ModAna2 = cprof:analyse(?MODULE, 2), - ?line {M2__1, [ModAna2]} = cprof:analyse(2), + ModAna2 = {?MODULE,M2__1,[{{?MODULE,seq_r,4},M}, + {{?MODULE,seq,3},M}]}, + ModAna2 = cprof:analyse(?MODULE, 2), + {M2__1, [ModAna2]} = cprof:analyse(2), %% 2 = cprof:pause(?MODULE, seq_r), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), %% - ?line ModAna3 = {?MODULE,M3__1,[{{?MODULE,seq,3},M2}, - {{?MODULE,seq_r,4},M}, - {{?MODULE,seq_r,3},1}]}, - ?line ModAna3 = cprof:analyse(?MODULE), + ModAna3 = {?MODULE,M3__1,[{{?MODULE,seq,3},M2}, + {{?MODULE,seq_r,4},M}, + {{?MODULE,seq_r,3},1}]}, + ModAna3 = cprof:analyse(?MODULE), %% - ?line N = cprof:pause(), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), + N = cprof:pause(), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), %% - ?line {M3__1, [ModAna3]} = cprof:analyse(), + {M3__1, [ModAna3]} = cprof:analyse(), %% - ?line N = cprof:restart(), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), + N = cprof:restart(), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), %% - ?line ModAna1 = cprof:analyse(?MODULE), + ModAna1 = cprof:analyse(?MODULE), %% - ?line N = cprof:stop(), - ?line {?MODULE,0,[]} = cprof:analyse(?MODULE), - ?line {0,[]} = cprof:analyse(), + N = cprof:stop(), + {?MODULE,0,[]} = cprof:analyse(?MODULE), + {0,[]} = cprof:analyse(), ok. %% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% on_load_test(Config) -> - ?line Priv = ?config(priv_dir, Config), - ?line Data = ?config(data_dir, Config), - ?line File = filename:join(Data, "cprof_SUITE_test"), - ?line Module = cprof_SUITE_test, - ?line M = 1000, + Priv = proplists:get_value(priv_dir, Config), + Data = proplists:get_value(data_dir, Config), + File = filename:join(Data, "cprof_SUITE_test"), + Module = cprof_SUITE_test, + M = 1000, %% - ?line M2 = M*2, - ?line M2__1 = M2 + 1, - ?line N1 = cprof:start(), + M2 = M*2, + M2__1 = M2 + 1, + N1 = cprof:start(), - ?line {ok,Module} = c:c(File, [{outdir,Priv}]), + {ok,Module} = c:c(File, [{outdir,Priv}]), %% If this system is hipe-enabled, the loader may have called module_info/1 %% when Module was loaded above. Reset the call count to avoid seeing %% the call in the analysis below. - ?line 1 = cprof:restart(Module, module_info, 1), - - ?line L = Module:seq(1, M, fun succ/1), - ?line Lr = Module:seq_r(1, M, fun succ/1), - ?line Lr = lists:reverse(L), - ?line N2 = cprof:pause(), - ?line N3 = cprof:pause(Module), - ?line {Module,M2__1,[{{Module,seq_r,4},M}, - {{Module,seq,3},M}, - {{Module,seq_r,3},1}]} = cprof:analyse(Module), - ?line io:format("~p ~p ~p~n", [N1, N2, N3]), - ?line code:purge(Module), - ?line code:delete(Module), - ?line N4 = N2 - N3, + 1 = cprof:restart(Module, module_info, 1), + + L = Module:seq(1, M, fun succ/1), + Lr = Module:seq_r(1, M, fun succ/1), + Lr = lists:reverse(L), + N2 = cprof:pause(), + N3 = cprof:pause(Module), + {Module,M2__1,[{{Module,seq_r,4},M}, + {{Module,seq,3},M}, + {{Module,seq_r,3},1}]} = cprof:analyse(Module), + io:format("~p ~p ~p~n", [N1, N2, N3]), + code:purge(Module), + code:delete(Module), + N4 = N2 - N3, %% - ?line N4 = cprof:restart(), - ?line {ok,Module} = c:c(File, [{outdir,Priv}]), - ?line L = Module:seq(1, M, fun succ/1), - ?line Lr = Module:seq_r(1, M, fun succ/1), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), - ?line N2 = cprof:pause(), - ?line {Module,0,[]} = cprof:analyse(Module), - ?line M_1 = M - 1, - ?line M4__4 = M*4 - 4, - ?line M10_7 = M*10 - 7, - ?line {?MODULE,M10_7,[{{?MODULE,succ,1},M4__4}, - {{?MODULE,seq_r,4},M}, - {{?MODULE,seq,3},M}, - {{?MODULE,'-on_load_test/1-fun-5-',1},M_1}, - {{?MODULE,'-on_load_test/1-fun-4-',1},M_1}, - {{?MODULE,'-on_load_test/1-fun-3-',1},M_1}, - {{?MODULE,'-on_load_test/1-fun-2-',1},M_1}, - {{?MODULE,seq_r,3},1}]} - = cprof:analyse(?MODULE), - ?line N2 = cprof:stop(), + N4 = cprof:restart(), + {ok,Module} = c:c(File, [{outdir,Priv}]), + L = Module:seq(1, M, fun succ/1), + Lr = Module:seq_r(1, M, fun succ/1), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), + N2 = cprof:pause(), + {Module,0,[]} = cprof:analyse(Module), + M_1 = M - 1, + M4__4 = M*4 - 4, + M10_7 = M*10 - 7, + {?MODULE,M10_7,[{{?MODULE,succ,1},M4__4}, + {{?MODULE,seq_r,4},M}, + {{?MODULE,seq,3},M}, + {{?MODULE,'-on_load_test/1-fun-5-',1},M_1}, + {{?MODULE,'-on_load_test/1-fun-4-',1},M_1}, + {{?MODULE,'-on_load_test/1-fun-3-',1},M_1}, + {{?MODULE,'-on_load_test/1-fun-2-',1},M_1}, + {{?MODULE,seq_r,3},1}]} + = cprof:analyse(?MODULE), + N2 = cprof:stop(), ok. %% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% modules_test(Config) -> - ?line Priv = ?config(priv_dir, Config), - ?line Data = ?config(data_dir, Config), - ?line File = filename:join(Data, "cprof_SUITE_test"), - ?line Module = cprof_SUITE_test, - ?line {ok,Module} = c:c(File, [{outdir,Priv}]), - ?line M = 10, + Priv = proplists:get_value(priv_dir, Config), + Data = proplists:get_value(data_dir, Config), + File = filename:join(Data, "cprof_SUITE_test"), + Module = cprof_SUITE_test, + {ok,Module} = c:c(File, [{outdir,Priv}]), + M = 10, %% - ?line M2 = M*2, - ?line M2__1 = M2 + 1, - ?line erlang:yield(), - ?line N = cprof:start(), - ?line L = Module:seq(1, M, fun succ/1), - ?line Lr = Module:seq_r(1, M, fun succ/1), - ?line L = seq(1, M, fun succ/1), - ?line Lr = seq_r(1, M, fun succ/1), - ?line N = cprof:pause(), - ?line Lr = lists:reverse(L), - ?line M_1 = M - 1, - ?line M4_4 = M*4 - 4, - ?line M10_7 = M*10 - 7, - ?line M2__1 = M*2 + 1, - ?line {Tot,ModList} = cprof:analyse(), - ?line {value,{?MODULE,M10_7,[{{?MODULE,succ,1},M4_4}, - {{?MODULE,seq_r,4},M}, - {{?MODULE,seq,3},M}, - {{?MODULE,'-modules_test/1-fun-3-',1},M_1}, - {{?MODULE,'-modules_test/1-fun-2-',1},M_1}, - {{?MODULE,'-modules_test/1-fun-1-',1},M_1}, - {{?MODULE,'-modules_test/1-fun-0-',1},M_1}, - {{?MODULE,seq_r,3},1}]}} = - lists:keysearch(?MODULE, 1, ModList), - ?line {value,{Module,M2__1,[{{Module,seq_r,4},M}, - {{Module,seq,3},M}, - {{Module,seq_r,3},1}]}} = - lists:keysearch(Module, 1, ModList), - ?line Tot = lists:foldl(fun ({_,C,_}, A) -> C+A end, 0, ModList), - ?line {cprof,_,Prof} = cprof:analyse(cprof), - ?line {value,{{cprof,pause,0},1}} = - lists:keysearch({cprof,pause,0}, 1, Prof), - ?line N = cprof:stop(), + M2 = M*2, + M2__1 = M2 + 1, + erlang:yield(), + N = cprof:start(), + L = Module:seq(1, M, fun succ/1), + Lr = Module:seq_r(1, M, fun succ/1), + L = seq(1, M, fun succ/1), + Lr = seq_r(1, M, fun succ/1), + N = cprof:pause(), + Lr = lists:reverse(L), + M_1 = M - 1, + M4_4 = M*4 - 4, + M10_7 = M*10 - 7, + M2__1 = M*2 + 1, + {Tot,ModList} = cprof:analyse(), + {value,{?MODULE,M10_7,[{{?MODULE,succ,1},M4_4}, + {{?MODULE,seq_r,4},M}, + {{?MODULE,seq,3},M}, + {{?MODULE,'-modules_test/1-fun-3-',1},M_1}, + {{?MODULE,'-modules_test/1-fun-2-',1},M_1}, + {{?MODULE,'-modules_test/1-fun-1-',1},M_1}, + {{?MODULE,'-modules_test/1-fun-0-',1},M_1}, + {{?MODULE,seq_r,3},1}]}} = + lists:keysearch(?MODULE, 1, ModList), + {value,{Module,M2__1,[{{Module,seq_r,4},M}, + {{Module,seq,3},M}, + {{Module,seq_r,3},1}]}} = + lists:keysearch(Module, 1, ModList), + Tot = lists:foldl(fun ({_,C,_}, A) -> C+A end, 0, ModList), + {cprof,_,Prof} = cprof:analyse(cprof), + {value,{{cprof,pause,0},1}} = lists:keysearch({cprof,pause,0}, 1, Prof), + N = cprof:stop(), ok. @@ -303,7 +276,6 @@ modules_test(Config) -> %% Local helpers - %% Stack recursive seq seq(Stop, Stop, Succ) when is_function(Succ) -> [Stop]; @@ -322,6 +294,5 @@ seq_r(Start, Stop, Succ, R) -> seq_r(Succ(Start), Stop, Succ, [Start | R]). - %% Successor succ(X) -> X+1. diff --git a/lib/tools/test/emacs_SUITE.erl b/lib/tools/test/emacs_SUITE.erl index 0c2d077e5d..77a8813db5 100644 --- a/lib/tools/test/emacs_SUITE.erl +++ b/lib/tools/test/emacs_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2005-2013. All Rights Reserved. +%% Copyright Ericsson AB 2005-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. diff --git a/lib/tools/test/emem_SUITE.erl b/lib/tools/test/emem_SUITE.erl index 93d21623ce..6dca7f6739 100644 --- a/lib/tools/test/emem_SUITE.erl +++ b/lib/tools/test/emem_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2005-2011. All Rights Reserved. +%% Copyright Ericsson AB 2005-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -19,15 +19,11 @@ %% -module(emem_SUITE). -%%-define(line_trace, 1). - --export([init_per_suite/1, end_per_suite/1, +-export([all/0, suite/0, + init_per_testcase/2, end_per_testcase/2, + init_per_suite/1, end_per_suite/1, receive_and_save_trace/2, send_trace/2]). - --export([all/0, suite/0,groups/0,init_per_group/2,end_per_group/2, - init_per_testcase/2, end_per_testcase/2]). - -export([live_node/1, 'sparc_sunos5.8_32b_emt2.0'/1, 'pc_win2000_32b_emt2.0'/1, @@ -42,11 +38,8 @@ 'sparc_sunos5.8_64b_emt1.0'/1]). -include_lib("kernel/include/file.hrl"). - -include_lib("common_test/include/ct.hrl"). --define(DEFAULT_TIMEOUT, ?t:minutes(5)). - -define(EMEM_64_32_COMMENT, "64 bit trace; this build of emem can only handle 32 bit traces"). @@ -62,28 +55,19 @@ exit_code}). %% -%% %% Exported suite functions %% -%% -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{minutes,5}}]. all() -> - case is_debug_compiled() of - true -> {skip, "Not run when debug compiled"}; - false -> test_cases() + case test_server:is_debug() of + true -> {skip, "Not run when debug compiled"}; + false -> test_cases() end. -groups() -> - []. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - test_cases() -> [live_node, 'sparc_sunos5.8_32b_emt2.0', @@ -99,31 +83,26 @@ test_cases() -> init_per_testcase(Case, Config) when is_list(Config) -> case maybe_skip(Config) of - {skip, _}=Skip -> Skip; + {skip, _}=Skip -> + Skip; ok -> - Dog = ?t:timetrap(?DEFAULT_TIMEOUT), - %% Until emem is completely stable we run these tests in a working %% directory with an ignore_core_files file which will make the %% search for core files ignore cores generated by this suite. - ignore_cores:setup(?MODULE, - Case, - [{watchdog, Dog}, {testcase, Case} | Config]) + ignore_cores:setup(?MODULE, Case, [{testcase, Case}|Config]) end. end_per_testcase(_Case, Config) when is_list(Config) -> ignore_cores:restore(Config), - Dog = ?config(watchdog, Config), - ?t:timetrap_cancel(Dog), ok. maybe_skip(Config) -> - DataDir = ?config(data_dir, Config), + DataDir = proplists:get_value(data_dir, Config), case filelib:is_dir(DataDir) of false -> {skip, "No data directory"}; true -> - case ?config(emem, Config) of + case proplists:get_value(emem, Config) of undefined -> {skip, "emem not found"}; _ -> @@ -159,13 +138,11 @@ end_per_suite(Config) when is_list(Config) -> %% %% -live_node(doc) -> []; -live_node(suite) -> []; live_node(Config) when is_list(Config) -> - ?line {ok, EmuFlag, Port} = start_emem(Config), - ?line Nodename = mk_nodename(Config), - ?line {ok, Node} = start_node(Nodename, EmuFlag), - ?line NP = spawn(Node, + {ok, EmuFlag, Port} = start_emem(Config), + Nodename = mk_nodename(Config), + {ok, Node} = start_node(Nodename, EmuFlag), + NP = spawn(Node, fun () -> receive go -> ok end, I = spawn(fun () -> ignorer end), @@ -187,246 +164,216 @@ live_node(Config) when is_list(Config) -> GC(), GC() end), - ?line MRef = erlang:monitor(process, NP), + MRef = erlang:monitor(process, NP), NP ! go, - ?line receive + receive {'DOWN', MRef, process, NP, Reason} -> - ?line spawn(Node, fun () -> halt(17) end), - ?line normal = Reason + spawn(Node, fun () -> halt(17) end), + normal = Reason end, - ?line Res = get_emem_result(Port), - ?line {ok, Hostname} = inet:gethostname(), - ?line ShortHostname = short_hostname(Hostname), - ?line {true, _} = has_prefix(Nodename, Res#emem_res.nodename), - ?line ShortHostname = short_hostname(Res#emem_res.hostname), - ?line Bits = case erlang:system_info(wordsize) of - 4 -> ?line "32 bits"; - 8 -> ?line "64 bits" + Res = get_emem_result(Port), + {ok, Hostname} = inet:gethostname(), + ShortHostname = short_hostname(Hostname), + {true, _} = has_prefix(Nodename, Res#emem_res.nodename), + ShortHostname = short_hostname(Res#emem_res.hostname), + Bits = case erlang:system_info(wordsize) of + 4 -> "32 bits"; + 8 -> "64 bits" end, - ?line Bits = Res#emem_res.word_size, - ?line "17" = Res#emem_res.exit_code, - ?line emem_comment(Config). + Bits = Res#emem_res.word_size, + "17" = Res#emem_res.exit_code, + emem_comment(Config). -'sparc_sunos5.8_32b_emt2.0'(doc) -> []; -'sparc_sunos5.8_32b_emt2.0'(suite) -> []; 'sparc_sunos5.8_32b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "gorbag" = Res#emem_res.hostname, - ?line "17074" = Res#emem_res.pid, - ?line "2005-01-14 17:28:37.881980" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["15", - "2665739", "8992", "548986", "16131", "539994", - "4334192", "1", "99", "15", "98", - "0", "0", "49", "0", "49"] = Res#emem_res.last_values, - ?line ["5972061", "9662", - "7987824", "5", - "2375680", "3"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). - -'pc_win2000_32b_emt2.0'(doc) -> []; -'pc_win2000_32b_emt2.0'(suite) -> []; + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "gorbag" = Res#emem_res.hostname, + "17074" = Res#emem_res.pid, + "2005-01-14 17:28:37.881980" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["15", "2665739", "8992", "548986", "16131", "539994", + "4334192", "1", "99", "15", "98", + "0", "0", "49", "0", "49"] = Res#emem_res.last_values, + ["5972061", "9662", "7987824", "5", + "2375680", "3"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). + 'pc_win2000_32b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "E-788FCF5191B54" = Res#emem_res.hostname, - ?line "504" = Res#emem_res.pid, - ?line "2005-01-24 17:27:28.224000" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["11", - "2932575", "8615", "641087", "68924", "632472"] + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "E-788FCF5191B54" = Res#emem_res.hostname, + "504" = Res#emem_res.pid, + "2005-01-24 17:27:28.224000" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["11", "2932575", "8615", "641087", "68924", "632472"] = Res#emem_res.last_values, - ?line ["5434206", "9285"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). + ["5434206", "9285"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). -'pc.smp_linux2.2.19pre17_32b_emt2.0'(doc) -> []; -'pc.smp_linux2.2.19pre17_32b_emt2.0'(suite) -> []; 'pc.smp_linux2.2.19pre17_32b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "four-roses" = Res#emem_res.hostname, - ?line "20689" = Res#emem_res.pid, - ?line "2005-01-20 13:11:26.143077" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["49", - "2901817", "9011", "521610", "10875", "512599", - "5392096", "2", "120", "10", "118", - "0", "0", "59", "0", "59"] = Res#emem_res.last_values, - ?line ["6182918", "9681", - "9062112", "6", - "2322432", "3"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). - - -'powerpc_darwin7.7.0_32b_emt2.0'(doc) -> []; -'powerpc_darwin7.7.0_32b_emt2.0'(suite) -> []; + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "four-roses" = Res#emem_res.hostname, + "20689" = Res#emem_res.pid, + "2005-01-20 13:11:26.143077" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["49", "2901817", "9011", "521610", "10875", "512599", + "5392096", "2", "120", "10", "118", + "0", "0", "59", "0", "59"] = Res#emem_res.last_values, + ["6182918", "9681", + "9062112", "6", + "2322432", "3"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). + + 'powerpc_darwin7.7.0_32b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "grima" = Res#emem_res.hostname, - ?line "13021" = Res#emem_res.pid, - ?line "2005-01-20 15:08:17.568668" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["9", - "2784323", "8641", "531105", "15893", "522464"] + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "grima" = Res#emem_res.hostname, + "13021" = Res#emem_res.pid, + "2005-01-20 15:08:17.568668" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["9", "2784323", "8641", "531105", "15893", "522464"] = Res#emem_res.last_values, - ?line ["6150376", "9311"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). + ["6150376", "9311"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). -'alpha_osf1v5.1_64b_emt2.0'(doc) -> []; -'alpha_osf1v5.1_64b_emt2.0'(suite) -> []; 'alpha_osf1v5.1_64b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "thorin" = Res#emem_res.hostname, - ?line "224630" = Res#emem_res.pid, - ?line "2005-01-20 22:38:01.299632" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "64 bits" = Res#emem_res.word_size, - ?line case Res#emem_res.max_word_size of - "32 bits" -> - ?line emem_comment(Config, ?EMEM_64_32_COMMENT); - "64 bits" -> - ?line ["22", - "6591992", "8625", "516785", "14805", "508160", - "11429184", "5", "127", "254", "122", - "0", "0", "61", "0", "61"] = Res#emem_res.last_values, - ?line ["7041775", "9295", - "11593024", "7", - "2097152", "3"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config) - end. - -'sparc_sunos5.8_64b_emt2.0'(doc) -> []; -'sparc_sunos5.8_64b_emt2.0'(suite) -> []; + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "thorin" = Res#emem_res.hostname, + "224630" = Res#emem_res.pid, + "2005-01-20 22:38:01.299632" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "64 bits" = Res#emem_res.word_size, + case Res#emem_res.max_word_size of + "32 bits" -> + emem_comment(Config, ?EMEM_64_32_COMMENT); + "64 bits" -> + ["22", + "6591992", "8625", "516785", "14805", "508160", + "11429184", "5", "127", "254", "122", + "0", "0", "61", "0", "61"] = Res#emem_res.last_values, + ["7041775", "9295", + "11593024", "7", + "2097152", "3"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config) + end. + 'sparc_sunos5.8_64b_emt2.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "test_server" = Res#emem_res.nodename, - ?line "gorbag" = Res#emem_res.hostname, - ?line "10907" = Res#emem_res.pid, - ?line "2005-01-20 13:48:34.677068" = Res#emem_res.start_time, - ?line "2.0" = Res#emem_res.trace_version, - ?line "64 bits" = Res#emem_res.word_size, - ?line case Res#emem_res.max_word_size of - "32 bits" -> - ?line emem_comment(Config, ?EMEM_64_32_COMMENT); - "64 bits" -> - ?line ["16", - "5032887", "8657", "530635", "14316", "521978", - "8627140", "5", "139", "19", "134", - "0", "0", "67", "0", "67"] = Res#emem_res.last_values, - ?line ["11695070", "9324", - "16360388", "10", - "4136960", "3"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config) - end. - -'sparc_sunos5.8_32b_emt1.0'(doc) -> []; -'sparc_sunos5.8_32b_emt1.0'(suite) -> []; + Res = run_emem_on_casefile(Config), + "test_server" = Res#emem_res.nodename, + "gorbag" = Res#emem_res.hostname, + "10907" = Res#emem_res.pid, + "2005-01-20 13:48:34.677068" = Res#emem_res.start_time, + "2.0" = Res#emem_res.trace_version, + "64 bits" = Res#emem_res.word_size, + case Res#emem_res.max_word_size of + "32 bits" -> + emem_comment(Config, ?EMEM_64_32_COMMENT); + "64 bits" -> + ["16", + "5032887", "8657", "530635", "14316", "521978", + "8627140", "5", "139", "19", "134", + "0", "0", "67", "0", "67"] = Res#emem_res.last_values, + ["11695070", "9324", + "16360388", "10", + "4136960", "3"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config) + end. + 'sparc_sunos5.8_32b_emt1.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "" = Res#emem_res.nodename, - ?line "" = Res#emem_res.hostname, - ?line "" = Res#emem_res.pid, - ?line "" = Res#emem_res.start_time, - ?line "1.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["11", - "2558261", "8643", "560610", "15325", "551967"] + Res = run_emem_on_casefile(Config), + "" = Res#emem_res.nodename, + "" = Res#emem_res.hostname, + "" = Res#emem_res.pid, + "" = Res#emem_res.start_time, + "1.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["11", "2558261", "8643", "560610", "15325", "551967"] = Res#emem_res.last_values, - ?line ["2791121", "9317"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). + ["2791121", "9317"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). -'pc_win2000_32b_emt1.0'(doc) -> []; -'pc_win2000_32b_emt1.0'(suite) -> []; 'pc_win2000_32b_emt1.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "" = Res#emem_res.nodename, - ?line "" = Res#emem_res.hostname, - ?line "" = Res#emem_res.pid, - ?line "" = Res#emem_res.start_time, - ?line "1.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["6", - "2965248", "8614", "640897", "68903", "632283"] + Res = run_emem_on_casefile(Config), + "" = Res#emem_res.nodename, + "" = Res#emem_res.hostname, + "" = Res#emem_res.pid, + "" = Res#emem_res.start_time, + "1.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["6", "2965248", "8614", "640897", "68903", "632283"] = Res#emem_res.last_values, - ?line ["3147090", "9283"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). + ["3147090", "9283"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). -'powerpc_darwin7.7.0_32b_emt1.0'(doc) -> []; -'powerpc_darwin7.7.0_32b_emt1.0'(suite) -> []; 'powerpc_darwin7.7.0_32b_emt1.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "" = Res#emem_res.nodename, - ?line "" = Res#emem_res.hostname, - ?line "" = Res#emem_res.pid, - ?line "" = Res#emem_res.start_time, - ?line "1.0" = Res#emem_res.trace_version, - ?line "32 bits" = Res#emem_res.word_size, - ?line ["8", - "2852991", "8608", "529662", "15875", "521054"] + Res = run_emem_on_casefile(Config), + "" = Res#emem_res.nodename, + "" = Res#emem_res.hostname, + "" = Res#emem_res.pid, + "" = Res#emem_res.start_time, + "1.0" = Res#emem_res.trace_version, + "32 bits" = Res#emem_res.word_size, + ["8", "2852991", "8608", "529662", "15875", "521054"] = Res#emem_res.last_values, - ?line ["3173335", "9278"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config). + ["3173335", "9278"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config). -'alpha_osf1v5.1_64b_emt1.0'(doc) -> []; -'alpha_osf1v5.1_64b_emt1.0'(suite) -> []; 'alpha_osf1v5.1_64b_emt1.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "" = Res#emem_res.nodename, - ?line "" = Res#emem_res.hostname, - ?line "" = Res#emem_res.pid, - ?line "" = Res#emem_res.start_time, - ?line "1.0" = Res#emem_res.trace_version, - ?line "64 bits" = Res#emem_res.word_size, - ?line case Res#emem_res.max_word_size of - "32 bits" -> - ?line emem_comment(Config, ?EMEM_64_32_COMMENT); - "64 bits" -> - ?line ["22", - "6820094", "8612", "515518", "14812", "506906"] - = Res#emem_res.last_values, - ?line ["7292413", "9282"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config) - end. - -'sparc_sunos5.8_64b_emt1.0'(doc) -> []; -'sparc_sunos5.8_64b_emt1.0'(suite) -> []; + Res = run_emem_on_casefile(Config), + "" = Res#emem_res.nodename, + "" = Res#emem_res.hostname, + "" = Res#emem_res.pid, + "" = Res#emem_res.start_time, + "1.0" = Res#emem_res.trace_version, + "64 bits" = Res#emem_res.word_size, + case Res#emem_res.max_word_size of + "32 bits" -> + emem_comment(Config, ?EMEM_64_32_COMMENT); + "64 bits" -> + ["22", + "6820094", "8612", "515518", "14812", "506906"] + = Res#emem_res.last_values, + ["7292413", "9282"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config) + end. + 'sparc_sunos5.8_64b_emt1.0'(Config) when is_list(Config) -> - ?line Res = run_emem_on_casefile(Config), - ?line "" = Res#emem_res.nodename, - ?line "" = Res#emem_res.hostname, - ?line "" = Res#emem_res.pid, - ?line "" = Res#emem_res.start_time, - ?line "1.0" = Res#emem_res.trace_version, - ?line "64 bits" = Res#emem_res.word_size, - ?line case Res#emem_res.max_word_size of - "32 bits" -> - ?line emem_comment(Config, ?EMEM_64_32_COMMENT); - "64 bits" -> - ?line ["15", - "4965746", "8234", "543940", "14443", "535706"] - = Res#emem_res.last_values, - ?line ["11697645", "8908"] = Res#emem_res.maximum, - ?line "0" = Res#emem_res.exit_code, - ?line emem_comment(Config) - end. + Res = run_emem_on_casefile(Config), + "" = Res#emem_res.nodename, + "" = Res#emem_res.hostname, + "" = Res#emem_res.pid, + "" = Res#emem_res.start_time, + "1.0" = Res#emem_res.trace_version, + "64 bits" = Res#emem_res.word_size, + case Res#emem_res.max_word_size of + "32 bits" -> + emem_comment(Config, ?EMEM_64_32_COMMENT); + "64 bits" -> + ["15", + "4965746", "8234", "543940", "14443", "535706"] + = Res#emem_res.last_values, + ["11697645", "8908"] = Res#emem_res.maximum, + "0" = Res#emem_res.exit_code, + emem_comment(Config) + end. %% %% @@ -444,84 +391,84 @@ receive_and_save_trace(PortNumber, FileName) when is_integer(PortNumber), receive_loop(Socket, File) -> receive - {tcp, Socket, Data} -> - ok = file:write(File, Data), - receive_loop(Socket, File); - {tcp_closed, Socket} -> - file:close(File), - ok; - {tcp_error, Socket, Reason} -> - file:close(File), - {error, Reason} + {tcp, Socket, Data} -> + ok = file:write(File, Data), + receive_loop(Socket, File); + {tcp_closed, Socket} -> + file:close(File), + ok; + {tcp_error, Socket, Reason} -> + file:close(File), + {error, Reason} end. send_trace({Host, PortNumber}, FileName) when is_list(Host), is_integer(PortNumber), is_list(FileName) -> - ?line {ok, F} = file:open(FileName, [read, compressed]), - ?line {ok, S} = gen_tcp:connect(Host, PortNumber, [inet,{packet, 0}]), - ?line send_loop(S, F); + {ok, F} = file:open(FileName, [read, compressed]), + {ok, S} = gen_tcp:connect(Host, PortNumber, [inet,{packet, 0}]), + send_loop(S, F); send_trace(EmuFlag, FileName) when is_list(EmuFlag), is_list(FileName) -> - ?line ["+Mit", IpAddrStr, PortNoStr] = string:tokens(EmuFlag, " :"), - ?line send_trace({IpAddrStr, list_to_integer(PortNoStr)}, FileName). + ["+Mit", IpAddrStr, PortNoStr] = string:tokens(EmuFlag, " :"), + send_trace({IpAddrStr, list_to_integer(PortNoStr)}, FileName). send_loop(Socket, File) -> - ?line case file:read(File, 128) of - {ok, Data} -> - ?line case gen_tcp:send(Socket, Data) of - ok -> ?line send_loop(Socket, File); - Error -> - ?line gen_tcp:close(Socket), - ?line file:close(File), - Error - end; - eof -> - ?line gen_tcp:close(Socket), - ?line file:close(File), - ?line ok; - Error -> - ?line gen_tcp:close(Socket), - ?line file:close(File), - ?line Error - end. + case file:read(File, 128) of + {ok, Data} -> + case gen_tcp:send(Socket, Data) of + ok -> send_loop(Socket, File); + Error -> + gen_tcp:close(Socket), + file:close(File), + Error + end; + eof -> + gen_tcp:close(Socket), + file:close(File), + ok; + Error -> + gen_tcp:close(Socket), + file:close(File), + Error + end. check_emem(Dir, Type) when is_atom(Type) -> - ExeSuffix = case ?t:os_type() of - {win32, _} -> ".exe"; - _ -> "" - end, + ExeSuffix = case os:type() of + {win32, _} -> ".exe"; + _ -> "" + end, TypeSuffix = case Type of - opt -> ""; - _ -> "." ++ atom_to_list(Type) - end, + opt -> ""; + _ -> "." ++ atom_to_list(Type) + end, Emem = "emem" ++ TypeSuffix ++ ExeSuffix, case check_file(filename:join([Dir, Emem])) of - not_found -> ok; - File -> - Comment = case Type of - opt -> ""; - _ -> "[emem " ++ atom_to_list(Type) ++ " compiled]" - end, - throw([{emem, File}, {emem_comment, Comment}]) + not_found -> ok; + File -> + Comment = case Type of + opt -> ""; + _ -> "[emem " ++ atom_to_list(Type) ++ " compiled]" + end, + throw([{emem, File}, {emem_comment, Comment}]) end. check_dir(DirName) -> case file:read_file_info(DirName) of - {ok, #file_info {type = directory, access = A}} when A == read; - A == read_write -> - DirName; - _ -> - not_found + {ok, #file_info {type = directory, access = A}} when A == read; + A == read_write -> + DirName; + _ -> + not_found end. check_file(FileName) -> case file:read_file_info(FileName) of - {ok, #file_info {type = regular, access = A}} when A == read; - A == read_write -> - ?line FileName; - _ -> - ?line not_found + {ok, #file_info {type = regular, access = A}} when A == read; + A == read_write -> + FileName; + _ -> + not_found end. emem_comment(Config) when is_list(Config) -> @@ -529,158 +476,158 @@ emem_comment(Config) when is_list(Config) -> emem_comment(Config, ExtraComment) when is_list(Config), is_list(ExtraComment) -> - case {?config(emem_comment, Config), ExtraComment} of - {"", ""} -> ?line ok; - {"", XC} -> ?line {comment, XC}; - {EmemC, ""} -> ?line {comment, EmemC}; - {EmemC, XC} -> ?line {comment, EmemC ++ " " ++ XC} + case {proplists:get_value(emem_comment, Config), ExtraComment} of + {"", ""} -> ok; + {"", XC} -> {comment, XC}; + {EmemC, ""} -> {comment, EmemC}; + {EmemC, XC} -> {comment, EmemC ++ " " ++ XC} end. run_emem_on_casefile(Config) -> - CaseName = atom_to_list(?config(testcase, Config)), - ?line File = filename:join([?config(data_dir, Config), CaseName ++ ".gz"]), - ?line case check_file(File) of - not_found -> - ?line ?t:fail({error, {filenotfound, File}}); - _ -> - ?line ok - end, - ?line {ok, EmuFlag, Port} = start_emem(Config), - ?line Parent = self(), - ?line Ref = make_ref(), - ?line spawn_link(fun () -> - SRes = send_trace(EmuFlag, File), - Parent ! {Ref, SRes} - end), - ?line Res = get_emem_result(Port), - ?line receive - {Ref, ok} -> - ?line ok; - {Ref, SendError} -> - ?line ?t:format("Send result: ~p~n", [SendError]) - end, - ?line Res. + CaseName = atom_to_list(proplists:get_value(testcase, Config)), + File = filename:join([proplists:get_value(data_dir, Config), CaseName ++ ".gz"]), + case check_file(File) of + not_found -> + ct:fail({error, {filenotfound, File}}); + _ -> + ok + end, + {ok, EmuFlag, Port} = start_emem(Config), + Parent = self(), + Ref = make_ref(), + spawn_link(fun () -> + SRes = send_trace(EmuFlag, File), + Parent ! {Ref, SRes} + end), + Res = get_emem_result(Port), + receive + {Ref, ok} -> + ok; + {Ref, SendError} -> + io:format("Send result: ~p~n", [SendError]) + end, + Res. get_emem_result(Port) -> - ?line {Res, LV} = get_emem_result(Port, {#emem_res{}, []}), - ?line Res#emem_res{last_values = string:tokens(LV, " ")}. + {Res, LV} = get_emem_result(Port, {#emem_res{}, []}), + Res#emem_res{last_values = string:tokens(LV, " ")}. get_emem_result(Port, {_EmemRes, _LastValues} = Res) -> - ?line case get_emem_line(Port) of - eof -> - ?line Res; - Line -> - ?line get_emem_result(Port, parse_emem_line(Line, Res)) - end. + case get_emem_line(Port) of + eof -> + Res; + Line -> + get_emem_result(Port, parse_emem_line(Line, Res)) + end. parse_emem_main_header_footer_line(Line, {ER, LV} = Res) -> %% Header - ?line case has_prefix("> Nodename:", Line) of - {true, NN} -> - ?line throw({ER#emem_res{nodename = strip(NN)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Hostname:", Line) of - {true, HN} -> - ?line throw({ER#emem_res{hostname = strip(HN)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Pid:", Line) of - {true, P} -> - ?line throw({ER#emem_res{pid = strip(P)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Start time (UTC):", Line) of - {true, ST} -> - ?line throw({ER#emem_res{start_time = strip(ST)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Actual trace version:", Line) of - {true, TV} -> - ?line throw({ER#emem_res{trace_version = strip(TV)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Maximum trace word size:", Line) of - {true, MWS} -> - ?line throw({ER#emem_res{max_word_size = strip(MWS)}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Actual trace word size:", Line) of - {true, WS} -> - ?line throw({ER#emem_res{word_size = strip(WS)}, LV}); - false -> ?line ok - end, + case has_prefix("> Nodename:", Line) of + {true, NN} -> + throw({ER#emem_res{nodename = strip(NN)}, LV}); + false -> ok + end, + case has_prefix("> Hostname:", Line) of + {true, HN} -> + throw({ER#emem_res{hostname = strip(HN)}, LV}); + false -> ok + end, + case has_prefix("> Pid:", Line) of + {true, P} -> + throw({ER#emem_res{pid = strip(P)}, LV}); + false -> ok + end, + case has_prefix("> Start time (UTC):", Line) of + {true, ST} -> + throw({ER#emem_res{start_time = strip(ST)}, LV}); + false -> ok + end, + case has_prefix("> Actual trace version:", Line) of + {true, TV} -> + throw({ER#emem_res{trace_version = strip(TV)}, LV}); + false -> ok + end, + case has_prefix("> Maximum trace word size:", Line) of + {true, MWS} -> + throw({ER#emem_res{max_word_size = strip(MWS)}, LV}); + false -> ok + end, + case has_prefix("> Actual trace word size:", Line) of + {true, WS} -> + throw({ER#emem_res{word_size = strip(WS)}, LV}); + false -> ok + end, %% Footer - ?line case has_prefix("> Maximum:", Line) of - {true, M} -> - ?line throw({ER#emem_res{maximum = string:tokens(M," ")}, LV}); - false -> ?line ok - end, - ?line case has_prefix("> Emulator exited with code:", Line) of - {true, EC} -> - ?line throw({ER#emem_res{exit_code = strip(EC)}, LV}); - false -> ?line ok - end, - ?line Res. + case has_prefix("> Maximum:", Line) of + {true, M} -> + throw({ER#emem_res{maximum = string:tokens(M," ")}, LV}); + false -> ok + end, + case has_prefix("> Emulator exited with code:", Line) of + {true, EC} -> + throw({ER#emem_res{exit_code = strip(EC)}, LV}); + false -> ok + end, + Res. parse_emem_header_line(_Line, {_ER, _LV} = Res) -> - ?line Res. - + Res. + parse_emem_value_line(Line, {EmemRes, _OldLastValues}) -> - ?line {EmemRes, Line}. + {EmemRes, Line}. parse_emem_line("", Res) -> - ?line Res; + Res; parse_emem_line(Line, Res) -> - ?line [Prefix | _] = Line, + [Prefix | _] = Line, case Prefix of - $> -> ?line catch parse_emem_main_header_footer_line(Line, Res); - $| -> ?line catch parse_emem_header_line(Line, Res); - _ -> ?line catch parse_emem_value_line(Line, Res) + $> -> catch parse_emem_main_header_footer_line(Line, Res); + $| -> catch parse_emem_header_line(Line, Res); + _ -> catch parse_emem_value_line(Line, Res) end. start_emem(Config) when is_list(Config) -> - ?line Emem = ?config(emem, Config), - ?line Cd = case ignore_cores:dir(Config) of - false -> []; - Dir -> [{cd, Dir}] - end, - ?line case open_port({spawn, Emem ++ " -t -n -o -i 1"}, - Cd ++ [{line, 1024}, eof]) of - Port when is_port(Port) -> ?line {ok, read_emu_flag(Port), Port}; - Error -> ?line ?t:fail(Error) - end. + Emem = proplists:get_value(emem, Config), + Cd = case ignore_cores:dir(Config) of + false -> []; + Dir -> [{cd, Dir}] + end, + case open_port({spawn, Emem ++ " -t -n -o -i 1"}, + Cd ++ [{line, 1024}, eof]) of + Port when is_port(Port) -> {ok, read_emu_flag(Port), Port}; + Error -> ct:fail(Error) + end. read_emu_flag(Port) -> - ?line Line = case get_emem_line(Port) of - eof -> ?line ?t:fail(unexpected_end_of_file); - L -> ?line L - end, - ?line case has_prefix("> Emulator command line argument:", Line) of - {true, EmuFlag} -> EmuFlag; - false -> ?line read_emu_flag(Port) - end. + Line = case get_emem_line(Port) of + eof -> ct:fail(unexpected_end_of_file); + L -> L + end, + case has_prefix("> Emulator command line argument:", Line) of + {true, EmuFlag} -> EmuFlag; + false -> read_emu_flag(Port) + end. get_emem_line(Port, Acc) -> - ?line receive - {Port, {data, {eol, Data}}} -> - ?line Res = case Acc of - [] -> ?line Data; - _ -> ?line lists:flatten([Acc|Data]) - end, - ?line ?t:format("~s", [Res]), - ?line Res; - {Port, {data, {noeol, Data}}} -> - ?line get_emem_line(Port, [Acc|Data]); - {Port, eof} -> - ?line port_close(Port), - ?line eof - end. + receive + {Port, {data, {eol, Data}}} -> + Res = case Acc of + [] -> Data; + _ -> lists:flatten([Acc|Data]) + end, + io:format("~s", [Res]), + Res; + {Port, {data, {noeol, Data}}} -> + get_emem_line(Port, [Acc|Data]); + {Port, eof} -> + port_close(Port), + eof + end. get_emem_line(Port) -> - ?line get_emem_line(Port, []). + get_emem_line(Port, []). short_hostname([]) -> []; @@ -697,28 +644,13 @@ has_prefix(_, _) -> false. strip(Str) -> string:strip(Str). - + mk_nodename(Config) -> - {A, B, C} = now(), + Us = erlang:monotonic_time(), atom_to_list(?MODULE) - ++ "-" ++ atom_to_list(?config(testcase, Config)) - ++ "-" ++ integer_to_list(A*1000000000000 + B*1000000 + C). + ++ "-" ++ atom_to_list(proplists:get_value(testcase, Config)) + ++ integer_to_list(Us). start_node(Name, Args) -> - ?line Pa = filename:dirname(code:which(?MODULE)), - ?line ?t:start_node(Name, peer, [{args, Args ++ " -pa " ++ Pa}]). - -% stop_node(Node) -> -% ?t:stop_node(Node). - -is_debug_compiled() -> -is_debug_compiled(erlang:system_info(system_version)). - -is_debug_compiled([$d,$e,$b,$u,$g | _]) -> - true; -is_debug_compiled([ _, _, _, _]) -> - false; -is_debug_compiled([]) -> - false; -is_debug_compiled([_|Rest]) -> - is_debug_compiled(Rest). + Pa = filename:dirname(code:which(?MODULE)), + test_server:start_node(Name, peer, [{args, Args ++ " -pa " ++ Pa}]). diff --git a/lib/tools/test/eprof_SUITE.erl b/lib/tools/test/eprof_SUITE.erl index 6274eabc37..e908413315 100644 --- a/lib/tools/test/eprof_SUITE.erl +++ b/lib/tools/test/eprof_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1996-2013. All Rights Reserved. +%% Copyright Ericsson AB 1996-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -21,40 +21,23 @@ -include_lib("common_test/include/ct.hrl"). --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2]). - +-export([all/0, suite/0]). -export([tiny/1,eed/1,basic/1,basic_option/1]). -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{seconds,60}}]. all() -> [basic, basic_option, tiny, eed]. -groups() -> - []. - -init_per_suite(Config) -> - Config. - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - - -basic(suite) -> []; basic(Config) when is_list(Config) -> %% load eprof_test and change directory {ok, OldCurDir} = file:get_cwd(), - Datadir = ?config(data_dir, Config), - Privdir = ?config(priv_dir, Config), + Datadir = proplists:get_value(data_dir, Config), + Privdir = proplists:get_value(priv_dir, Config), {ok,eprof_test} = compile:file(filename:join(Datadir, "eprof_test"), [trace,{outdir, Privdir}]), ok = file:set_cwd(Privdir), @@ -98,9 +81,6 @@ basic(Config) when is_list(Config) -> %% error case - error = eprof:profile([Pid], fun() -> eprof_test:go(10) end), - Pid = whereis(eprof), - error = eprof:profile([Pid], fun() -> eprof_test:go(10) end), A = spawn(fun() -> receive _ -> ok end end), profiling = eprof:profile([A]), true = exit(A, kill_it), @@ -139,8 +119,8 @@ basic_option_1(Config) -> %% load eprof_test and change directory {ok, OldCurDir} = file:get_cwd(), - Datadir = ?config(data_dir, Config), - Privdir = ?config(priv_dir, Config), + Datadir = proplists:get_value(data_dir, Config), + Privdir = proplists:get_value(priv_dir, Config), {ok,eprof_test} = compile:file(filename:join(Datadir, "eprof_test"), [trace,{outdir, Privdir}]), ok = file:set_cwd(Privdir), @@ -178,13 +158,11 @@ basic_option_1(Config) -> stopped = eprof:stop(), ok. -tiny(suite) -> []; tiny(Config) when is_list(Config) -> ensure_eprof_stopped(), {ok, OldCurDir} = file:get_cwd(), - Datadir = ?config(data_dir, Config), - Privdir = ?config(priv_dir, Config), - TTrap=?t:timetrap(60*1000), + Datadir = proplists:get_value(data_dir, Config), + Privdir = proplists:get_value(priv_dir, Config), % (Trace)Compile to priv_dir and make sure the correct version is loaded. {ok,eprof_suite_test} = compile:file(filename:join(Datadir, "eprof_suite_test"), @@ -200,16 +178,14 @@ tiny(Config) when is_list(Config) -> ok = eprof:analyze(total), ok = eprof:log("eprof_SUITE_logfile"), stopped = eprof:stop(), - ?t:timetrap_cancel(TTrap), ok = file:set_cwd(OldCurDir), ok. -eed(suite) -> []; eed(Config) when is_list(Config) -> ensure_eprof_stopped(), - Datadir = ?config(data_dir, Config), - Privdir = ?config(priv_dir, Config), - TTrap=?t:timetrap(5*60*1000), + Datadir = proplists:get_value(data_dir, Config), + Privdir = proplists:get_value(priv_dir, Config), + ct:timetrap({minutes, 5}), %% (Trace)Compile to priv_dir and make sure the correct version is loaded. code:purge(eed), @@ -236,7 +212,6 @@ eed(Config) when is_list(Config) -> ok = eprof:analyze(total), ok = eprof:log("eprof_SUITE_logfile"), stopped = eprof:stop(), - ?t:timetrap_cancel(TTrap), try S = lists:flatten(io_lib:format("~p times slower", [10*(T3-T2)/(T2-T1)])), diff --git a/lib/tools/test/fprof_SUITE.erl b/lib/tools/test/fprof_SUITE.erl index d1a673d6b7..affb45b7a6 100644 --- a/lib/tools/test/fprof_SUITE.erl +++ b/lib/tools/test/fprof_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2001-2012. All Rights Reserved. +%% Copyright Ericsson AB 2001-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -22,25 +22,20 @@ -include_lib("common_test/include/ct.hrl"). %% Test server framework exports --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2, not_run/1]). +-export([all/0, suite/0, not_run/1]). %% Test suites -export([stack_seq/1, tail_seq/1, create_file_slow/1, spawn_simple/1, - imm_tail_seq/1, imm_create_file_slow/1, imm_compile/1, - cpu_create_file_slow/1]). + imm_tail_seq/1, imm_create_file_slow/1, imm_compile/1, + cpu_create_file_slow/1]). %% Other exports -export([create_file_slow/2]). - %% Debug exports -export([parse/1, verify/2]). -export([spawn_simple_test/3]). - --define(line_trace,true). - %-define(debug,true). -ifdef(debug). -define(dbg(Str,Args), io:format(Str,Args)). @@ -49,553 +44,495 @@ -endif. - %%%--------------------------------------------------------------------- %%% Test suites %%%--------------------------------------------------------------------- - -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{seconds,60}}]. all() -> case test_server:is_native(fprof_SUITE) of - true -> [not_run]; - false -> - [stack_seq, tail_seq, create_file_slow, spawn_simple, - imm_tail_seq, imm_create_file_slow, imm_compile, - cpu_create_file_slow] + true -> [not_run]; + false -> + [stack_seq, tail_seq, create_file_slow, spawn_simple, + imm_tail_seq, imm_create_file_slow, imm_compile, + cpu_create_file_slow] end. -groups() -> - []. - -init_per_suite(Config) -> - Config. - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - not_run(Config) when is_list(Config) -> {skipped, "Native code"}. %%%--------------------------------------------------------------------- -stack_seq(doc) -> - ["Tests a stack recursive variant of lists:seq/3"]; -stack_seq(suite) -> - []; +%% Tests a stack recursive variant of lists:seq/3 stack_seq(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(20)), - ?line PrivDir = ?config(priv_dir, Config), - ?line TraceFile = - filename:join(PrivDir, ?MODULE_STRING"_stack_seq.trace"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_stack_seq.analysis"), - ?line Start = 1, - ?line Stop = 1000, - ?line Succ = fun (X) -> X + 1 end, - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + TraceFile = filename:join(PrivDir, + ?MODULE_STRING"_stack_seq.trace"), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_stack_seq.analysis"), + Start = 1, + Stop = 1000, + Succ = fun (X) -> X + 1 end, + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line R0 = fprof:apply(fun seq/3, [Start, Stop, Succ], [{file, TraceFile}]), - ?line TS1 = erlang:now(), - ?line R = seq(Start, Stop, Succ), - ?line TS2 = erlang:now(), - ?line ok = fprof:profile(file, TraceFile), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), - ?line R = R0, + TS0 = erlang:monotonic_time(), + R0 = fprof:apply(fun seq/3, [Start, Stop, Succ], [{file, TraceFile}]), + TS1 = erlang:monotonic_time(), + R = seq(Start, Stop, Succ), + TS2 = erlang:monotonic_time(), + ok = fprof:profile(file, TraceFile), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), + R = R0, %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = (catch verify(T, P)), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = (catch verify(T, P)), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> + ok + end, %% - ?line check_own_and_acc(TraceFile,AnalysisFile), + check_own_and_acc(TraceFile,AnalysisFile), %% - ?line ets:delete(T), - ?line file:delete(TraceFile), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc2 = ts_sub(TS2, TS1), - ?line io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc1, Acc2]), - {comment, io_lib:format("~p times slower", [Acc1/Acc2])}. + ets:delete(T), + file:delete(TraceFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc2 = TS2 - TS1, + io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc1, Acc2]), + {comment, io_lib:format("~p times slower", [divide(Acc1,Acc2)])}. %%%--------------------------------------------------------------------- -tail_seq(doc) -> - ["Tests a tail recursive variant of lists:seq/3"]; -tail_seq(suite) -> - []; +%% Tests a tail recursive variant of lists:seq/3 tail_seq(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(10)), - ?line PrivDir = ?config(priv_dir, Config), - ?line TraceFile = - filename:join(PrivDir, ?MODULE_STRING"_tail_seq.trace"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_tail_seq.analysis"), - ?line Start = 1, - ?line Stop = 1000, - ?line Succ = fun (X) -> X + 1 end, - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + TraceFile = filename:join(PrivDir, + ?MODULE_STRING"_tail_seq.trace"), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_tail_seq.analysis"), + Start = 1, + Stop = 1000, + Succ = fun (X) -> X + 1 end, + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line R = seq_r(Start, Stop, Succ), - ?line TS1 = erlang:now(), + TS0 = erlang:monotonic_time(), + R = seq_r(Start, Stop, Succ), + TS1 = erlang:monotonic_time(), %% - ?line R1 = fprof:apply(fun seq_r/3, [Start, Stop, Succ], - [{file, TraceFile}]), - ?line TS2 = erlang:now(), - ?line ok = fprof:profile([{file,TraceFile}]), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), - ?line R = R1, + R1 = fprof:apply(fun seq_r/3, [Start, Stop, Succ], + [{file, TraceFile}]), + TS2 = erlang:monotonic_time(), + ok = fprof:profile([{file,TraceFile}]), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), + R = R1, %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> + ok + end, %% - ?line check_own_and_acc(TraceFile,AnalysisFile), + check_own_and_acc(TraceFile,AnalysisFile), %% - ?line ets:delete(T), - ?line file:delete(TraceFile), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc2 = ts_sub(TS2, TS1), - ?line io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc2, Acc1]), - {comment, io_lib:format("~p times slower", [Acc2/Acc1])}. + ets:delete(T), + file:delete(TraceFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc2 = TS2 - TS1, + io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc2, Acc1]), + {comment, io_lib:format("~p times slower", [divide(Acc2,Acc1)])}. %%%--------------------------------------------------------------------- %% Tests the create_file_slow benchmark. create_file_slow(Config) -> case test_server:is_native(lists) orelse - test_server:is_native(file) of - true -> - {skip,"Native libs -- tracing does not work"}; - false -> - do_create_file_slow(Config) + test_server:is_native(file) of + true -> + {skip,"Native libs -- tracing does not work"}; + false -> + do_create_file_slow(Config) end. do_create_file_slow(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(40)), - ?line PrivDir = ?config(priv_dir, Config), - ?line TraceFile = - filename:join(PrivDir, ?MODULE_STRING"_create_file_slow.trace"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_create_file_slow.analysis"), - ?line DataFile = - filename:join(PrivDir, ?MODULE_STRING"_create_file_slow.data"), - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + TraceFile = filename:join(PrivDir, + ?MODULE_STRING"_create_file_slow.trace"), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_create_file_slow.analysis"), + DataFile = filename:join(PrivDir, + ?MODULE_STRING"_create_file_slow.data"), + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line ok = create_file_slow(DataFile, 1024), - ?line TS1 = erlang:now(), + TS0 = erlang:monotonic_time(), + ok = create_file_slow(DataFile, 1024), + TS1 = erlang:monotonic_time(), %% - ?line ok = file:delete(DataFile), - ?line TS2 = erlang:now(), - ?line ok = fprof:apply(?MODULE, create_file_slow, [DataFile, 1024], - [{file, TraceFile}]), - ?line TS3 = erlang:now(), - ?line ok = fprof:profile(file, TraceFile), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), + ok = file:delete(DataFile), + TS2 = erlang:monotonic_time(), + ok = fprof:apply(?MODULE, create_file_slow, [DataFile, 1024], + [{file, TraceFile}]), + TS3 = erlang:monotonic_time(), + ok = fprof:profile(file, TraceFile), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> + ok + end, %% - ?line check_own_and_acc(TraceFile,AnalysisFile), + check_own_and_acc(TraceFile,AnalysisFile), %% - ?line ets:delete(T), - ?line file:delete(DataFile), - ?line file:delete(TraceFile), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc3 = ts_sub(TS3, TS2), - ?line io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc3, Acc1]), - {comment, io_lib:format("~p times slower", [Acc3/Acc1])}. + ets:delete(T), + file:delete(DataFile), + file:delete(TraceFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc3 = TS3 - TS2, + io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc3, Acc1]), + {comment, io_lib:format("~p times slower", [divide(Acc3,Acc1)])}. %%%--------------------------------------------------------------------- -spawn_simple(doc) -> - ["Tests process spawn"]; -spawn_simple(suite) -> - []; +%% Tests process spawn spawn_simple(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(30)), - ?line PrivDir = ?config(priv_dir, Config), - ?line TraceFile = - filename:join(PrivDir, ?MODULE_STRING"_spawn_simple.trace"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_spawn_simple.analysis"), - ?line Start = 1, - ?line Stop = 1000, - ?line Succ = fun (X) -> X + 1 end, - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + TraceFile = filename:join(PrivDir, + ?MODULE_STRING"_spawn_simple.trace"), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_spawn_simple.analysis"), + Start = 1, + Stop = 1000, + Succ = fun (X) -> X + 1 end, + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line {{_, R1}, {_, R2}} = spawn_simple_test(Start, Stop, Succ), - ?line TS1 = erlang:now(), + TS0 = erlang:monotonic_time(), + {{_, R1}, {_, R2}} = spawn_simple_test(Start, Stop, Succ), + TS1 = erlang:monotonic_time(), %% - ?line ok = fprof:trace(start, TraceFile), - ?line {{P1, R3}, {P2, R4}} = spawn_simple_test(Start, Stop, Succ), - ?line ok = fprof:trace(stop), - ?line TS2 = erlang:now(), - ?line ok = fprof:profile(file, TraceFile), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), - ?line R1 = R3, - ?line R2 = R4, + ok = fprof:trace(start, TraceFile), + {{P1, R3}, {P2, R4}} = spawn_simple_test(Start, Stop, Succ), + ok = fprof:trace(stop), + TS2 = erlang:monotonic_time(), + ok = fprof:profile(file, TraceFile), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), + R1 = R3, + R2 = R4, %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc1 = pid_to_list(P1), - ?line Proc2 = pid_to_list(P2), - ?line Proc0 = pid_to_list(self()), - ?line io:format("~p~n ~p ~p ~p~n", [P, Proc0, Proc1, Proc2]), - ?line [{analysis_options, _}, [{totals, _, Acc, _}] | Procs] = P, - ?line [[{Proc0, _, undefined, _} | _]] = - lists:filter(fun ([Pt | _]) when element(1, Pt) == Proc0 -> true; - (_) -> false - end, Procs), - ?line [[{Proc1, _, undefined, _}, - {spawned_by, Proc0}, - {spawned_as, {erlang, apply, ["#Fun"++_, []]}}, - {initial_calls, [{erlang, apply, 2}, - {?MODULE, '-spawn_simple_test/3-fun-0-', 4}]} - | _]] = - lists:filter(fun ([Pt | _]) when element(1, Pt) == Proc1 -> true; - (_) -> false - end, Procs), - ?line [[{Proc2, _, undefined, _}, - {spawned_by, Proc0}, - {spawned_as, {erlang, apply, ["#Fun"++_, []]}}, - {initial_calls, [{erlang, apply, 2}, - {?MODULE, '-spawn_simple_test/3-fun-1-', 4}]} - | _]] = - lists:filter(fun ([Pt | _]) when element(1, Pt) == Proc2 -> true; - (_) -> false - end, Procs), - ?line 3 = length(Procs), - ?line R1 = lists:reverse(R2), + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc1 = pid_to_list(P1), + Proc2 = pid_to_list(P2), + Proc0 = pid_to_list(self()), + io:format("~p~n ~p ~p ~p~n", [P, Proc0, Proc1, Proc2]), + [{analysis_options, _}, [{totals, _, Acc, _}] | Procs] = P, + [[{Proc0, _, undefined, _} | _]] = lists:filter( + fun ([Pt | _]) when element(1, Pt) == Proc0 -> true; + (_) -> false + end, Procs), + [[{Proc1, _, undefined, _}, + {spawned_by, Proc0}, + {spawned_as, {erlang, apply, ["#Fun"++_, []]}}, + {initial_calls, [{erlang, apply, 2}, + {?MODULE, '-spawn_simple_test/3-fun-0-', 4}]} + | _]] = lists:filter(fun ([Pt | _]) when element(1, Pt) == Proc1 -> true; + (_) -> false + end, Procs), + [[{Proc2, _, undefined, _}, + {spawned_by, Proc0}, + {spawned_as, {erlang, apply, ["#Fun"++_, []]}}, + {initial_calls, [{erlang, apply, 2}, + {?MODULE, '-spawn_simple_test/3-fun-1-', 4}]} + | _]] = lists:filter(fun ([Pt | _]) when element(1, Pt) == Proc2 -> true; + (_) -> false + end, Procs), + 3 = length(Procs), + R1 = lists:reverse(R2), %% - ?line check_own_and_acc(TraceFile,AnalysisFile), + check_own_and_acc(TraceFile,AnalysisFile), %% - ?line ets:delete(T), - ?line file:delete(TraceFile), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc2 = ts_sub(TS2, TS1), - ?line io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc2, Acc1]), - {comment, io_lib:format("~p times slower", [Acc2/Acc1])}. + ets:delete(T), + file:delete(TraceFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc2 = TS2 - TS1, + io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc2, Acc1]), + {comment, io_lib:format("~p times slower", [divide(Acc2,Acc1)])}. spawn_simple_test(Start, Stop, Succ) -> Parent = self(), - Seq = - spawn_link( - fun () -> - Parent ! {self(), seq(Start, Stop, Succ)} - end), - SeqR = - spawn_link( - fun () -> - Parent ! {self(), seq_r(Start, Stop, Succ)} - end), - receive {Seq, SeqResult} -> - receive {SeqR, SeqRResult} -> - {{Seq, SeqResult}, {SeqR, SeqRResult}} - end + Seq = spawn_link(fun() -> + Parent ! {self(), seq(Start, Stop, Succ)} + end), + + SeqR = spawn_link(fun() -> + Parent ! {self(), seq_r(Start, Stop, Succ)} + end), + receive + {Seq, SeqResult} -> + receive + {SeqR, SeqRResult} -> + {{Seq, SeqResult}, {SeqR, SeqRResult}} + end end. %%%--------------------------------------------------------------------- -imm_tail_seq(doc) -> - ["Tests a tail recursive variant of lists:seq/3 ", - "with immediate trace to profile"]; -imm_tail_seq(suite) -> - []; +%% Tests a tail recursive variant of lists:seq/3 +%% with immediate trace to profile imm_tail_seq(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(10)), - ?line PrivDir = ?config(priv_dir, Config), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_imm_tail_seq.analysis"), - ?line Start = 1, - ?line Stop = 1000, - ?line Succ = fun (X) -> X + 1 end, - ?line ok = fprof:stop(kill), - ?line catch eprof:stop(), + PrivDir = proplists:get_value(priv_dir, Config), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_imm_tail_seq.analysis"), + Start = 1, + Stop = 1000, + Succ = fun (X) -> X + 1 end, + ok = fprof:stop(kill), + catch eprof:stop(), %% - ?line TS0 = erlang:now(), - ?line R0 = seq_r(Start, Stop, Succ), - ?line TS1 = erlang:now(), + TS0 = erlang:monotonic_time(), + R0 = seq_r(Start, Stop, Succ), + TS1 = erlang:monotonic_time(), %% - ?line profiling = eprof:start_profiling([self()]), - ?line TS2 = erlang:now(), - ?line R2 = seq_r(Start, Stop, Succ), - ?line TS3 = erlang:now(), - ?line profiling_stopped = eprof:stop_profiling(), - ?line R2 = R0, + profiling = eprof:start_profiling([self()]), + TS2 = erlang:monotonic_time(), + R2 = seq_r(Start, Stop, Succ), + TS3 = erlang:monotonic_time(), + profiling_stopped = eprof:stop_profiling(), + R2 = R0, %% - ?line eprof:analyze(), - ?line stopped = eprof:stop(), + eprof:analyze(), + stopped = eprof:stop(), %% - ?line {ok, Tracer} = fprof:profile(start), - ?line ok = fprof:trace([start, {tracer, Tracer}]), - ?line TS4 = erlang:now(), - ?line R4 = seq_r(Start, Stop, Succ), - ?line TS5 = erlang:now(), - ?line ok = fprof:trace(stop), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), - ?line R4 = R0, + {ok, Tracer} = fprof:profile(start), + ok = fprof:trace([start, {tracer, Tracer}]), + TS4 = erlang:monotonic_time(), + R4 = seq_r(Start, Stop, Succ), + TS5 = erlang:monotonic_time(), + ok = fprof:trace(stop), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), + R4 = R0, %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> ok + end, %% - ?line ets:delete(T), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc3 = ts_sub(TS3, TS2), - ?line Acc5 = ts_sub(TS5, TS4), - ?line io:format("~p (plain), ~p (eprof), ~p (fprof), ~p (cpu)~n", - [Acc1/1000, Acc3/1000, Acc5/1000, Acc/1000]), + ets:delete(T), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc3 = TS3 - TS2, + Acc5 = TS5 - TS4, + io:format("~p (plain), ~p (eprof), ~p (fprof), ~p (cpu)~n", + [Acc1/1000, Acc3/1000, Acc5/1000, Acc/1000]), {comment, io_lib:format("~p/~p (fprof/eprof) times slower", - [Acc5/Acc1, Acc3/Acc1])}. + [divide(Acc5,Acc1), divide(Acc3,Acc1)])}. %%%--------------------------------------------------------------------- -imm_create_file_slow(doc) -> - ["Tests a tail recursive variant of lists:seq/3 ", - "with immediate trace to profile"]; -imm_create_file_slow(suite) -> - []; +%% Tests a tail recursive variant of lists:seq/3 +%% with immediate trace to profile imm_create_file_slow(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(60)), - ?line PrivDir = ?config(priv_dir, Config), - ?line DataFile = - filename:join(PrivDir, ?MODULE_STRING"_imm_create_file_slow.data"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_imm_create_file_slow.analysis"), - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + DataFile = filename:join(PrivDir, + ?MODULE_STRING"_imm_create_file_slow.data"), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_imm_create_file_slow.analysis"), + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line ok = create_file_slow(DataFile, 1024), - ?line TS1 = erlang:now(), - ?line ok = file:delete(DataFile), + TS0 = erlang:monotonic_time(), + ok = create_file_slow(DataFile, 1024), + TS1 = erlang:monotonic_time(), + ok = file:delete(DataFile), %% - ?line {ok, Tracer} = fprof:profile(start), - ?line TS2 = erlang:now(), - ?line ok = fprof:apply(?MODULE, create_file_slow, [DataFile, 1024], - [{tracer, Tracer}, continue]), - ?line TS3 = erlang:now(), - ?line ok = fprof:profile(stop), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), + {ok, Tracer} = fprof:profile(start), + TS2 = erlang:monotonic_time(), + ok = fprof:apply(?MODULE, create_file_slow, [DataFile, 1024], + [{tracer, Tracer}, continue]), + TS3 = erlang:monotonic_time(), + ok = fprof:profile(stop), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> + ok + end, %% - ?line ets:delete(T), - ?line file:delete(DataFile), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc3 = ts_sub(TS3, TS2), - ?line io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc3, Acc1]), - {comment, io_lib:format("~p times slower", [Acc3/Acc1])}. + ets:delete(T), + file:delete(DataFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + Acc3 = TS3 - TS2, + io:format("ts:~w, fprof:~w, bare:~w.~n", [Acc, Acc3, Acc1]), + {comment, io_lib:format("~p times slower", [divide(Acc3,Acc1)])}. %%%--------------------------------------------------------------------- -imm_compile(doc) -> - ["Tests to compile a small source file ", - "with immediate trace to profile"]; -imm_compile(suite) -> - []; +%% Tests to compile a small source file with immediate trace to profile imm_compile(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:minutes(20)), - ?line DataDir = ?config(data_dir, Config), - ?line SourceFile = filename:join(DataDir, "foo.erl"), - ?line PrivDir = ?config(priv_dir, Config), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_imm_compile.analysis"), - ?line ok = fprof:stop(kill), - ?line catch eprof:stop(), + ct:timetrap({minutes, 20}), + DataDir = proplists:get_value(data_dir, Config), + SourceFile = filename:join(DataDir, "foo.erl"), + PrivDir = proplists:get_value(priv_dir, Config), + AnalysisFile = filename:join(PrivDir, + ?MODULE_STRING"_imm_compile.analysis"), + ok = fprof:stop(kill), + catch eprof:stop(), %% - ?line {ok, foo, _} = compile:file(SourceFile, [binary]), - ?line TS0 = erlang:now(), - ?line {ok, foo, _} = compile:file(SourceFile, [binary]), - ?line TS1 = erlang:now(), + {ok, foo, _} = compile:file(SourceFile, [binary]), + TS0 = erlang:monotonic_time(), + {ok, foo, _} = compile:file(SourceFile, [binary]), + TS1 = erlang:monotonic_time(), %% - ?line profiling = eprof:start_profiling([self()]), - ?line TS2 = erlang:now(), - ?line {ok, foo, _} = compile:file(SourceFile, [binary]), - ?line TS3 = erlang:now(), - ?line profiling_stopped = eprof:stop_profiling(), + profiling = eprof:start_profiling([self()]), + TS2 = erlang:monotonic_time(), + {ok, foo, _} = compile:file(SourceFile, [binary]), + TS3 = erlang:monotonic_time(), + profiling_stopped = eprof:stop_profiling(), %% - ?line eprof:analyze(), - ?line stopped = eprof:stop(), + eprof:analyze(), + stopped = eprof:stop(), %% - ?line {ok, Tracer} = fprof:profile(start), - ?line ok = fprof:trace([start, {tracer, Tracer}]), - ?line TS4 = erlang:now(), - ?line {ok, foo, _} = compile:file(SourceFile, [binary]), - ?line TS5 = erlang:now(), - ?line ok = fprof:trace(stop), + {ok, Tracer} = fprof:profile(start), + ok = fprof:trace([start, {tracer, Tracer}]), + TS4 = erlang:monotonic_time(), + {ok, foo, _} = compile:file(SourceFile, [binary]), + TS5 = erlang:monotonic_time(), + ok = fprof:trace(stop), %% - ?line io:format("Analysing...~n"), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), + io:format("Analysing...~n"), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n", [P]), - ?line Acc1 = ts_sub(TS1, TS0), - ?line Acc3 = ts_sub(TS3, TS2), - ?line Acc5 = ts_sub(TS5, TS4), - ?line io:format("Verifying...~n"), - ?line ok = verify(T, P), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}] | _] -> - ok - end, + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n", [P]), + Acc1 = TS1 - TS0, + Acc3 = TS3 - TS2, + Acc5 = TS5 - TS4, + io:format("Verifying...~n"), + ok = verify(T, P), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}] | _] -> + ok + end, %% - ?line ets:delete(T), - ?line file:delete(AnalysisFile), - ?line ?t:timetrap_cancel(Timetrap), - ?line io:format("~p (plain), ~p (eprof), ~p (fprof), ~p(cpu)~n", - [Acc1/1000, Acc3/1000, Acc5/1000, Acc/1000]), + ets:delete(T), + file:delete(AnalysisFile), + io:format("~p (plain), ~p (eprof), ~p (fprof), ~p(cpu)~n", + [Acc1/1000, Acc3/1000, Acc5/1000, Acc/1000]), {comment, io_lib:format("~p/~p (fprof/eprof) times slower", - [Acc5/Acc1, Acc3/Acc1])}. + [divide(Acc5,Acc1), divide(Acc3,Acc1)])}. %%%--------------------------------------------------------------------- -cpu_create_file_slow(doc) -> - ["Tests the create_file_slow benchmark using cpu_time"]; -cpu_create_file_slow(suite) -> - []; +%% Tests the create_file_slow benchmark using cpu_time cpu_create_file_slow(Config) when is_list(Config) -> - ?line Timetrap = ?t:timetrap(?t:seconds(40)), - ?line PrivDir = ?config(priv_dir, Config), - ?line TraceFile = - filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.trace"), - ?line AnalysisFile = - filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.analysis"), - ?line DataFile = - filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.data"), - ?line ok = fprof:stop(kill), + PrivDir = proplists:get_value(priv_dir, Config), + TraceFile = + filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.trace"), + AnalysisFile = + filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.analysis"), + DataFile = + filename:join(PrivDir, ?MODULE_STRING"_cpu_create_file_slow.data"), + ok = fprof:stop(kill), %% - ?line TS0 = erlang:now(), - ?line Result = (catch fprof:apply(?MODULE, create_file_slow, - [DataFile, 1024], - [{file, TraceFile}, cpu_time])), - ?line TS1 = erlang:now(), - ?line TestResult = - case Result of - ok -> - ?line ok = fprof:profile(file, TraceFile), - ?line ok = fprof:analyse(), - ?line ok = fprof:analyse(dest, AnalysisFile), - ?line ok = fprof:stop(), - %% - ?line {ok, [T, P]} = parse(AnalysisFile), - ?line io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), - ?line ok = verify(T, P), - ?line Proc = pid_to_list(self()), - ?line case P of - [{analysis_options, _}, - [{totals, _, Acc, _}], - [{Proc, _, undefined, _} | _]] -> - ok - end, - %% - ?line check_own_and_acc(TraceFile,AnalysisFile), - %% - ?line ets:delete(T), - ?line file:delete(DataFile), - ?line file:delete(TraceFile), - ?line file:delete(AnalysisFile), - ?line Acc1 = ts_sub(TS1, TS0), - ?line io:format("cpu_ts:~w, fprof:~w~n", [Acc, Acc1]), - {comment, io_lib:format("~p% cpu utilization", - [100*Acc/Acc1])}; - {'EXIT', not_supported} -> - case {os:type(), os:version()} of - {{unix, sunos}, {Major, Minor, _}} - when Major >= 5, Minor >= 7 -> - test_server:fail(Result); - _ -> - {skipped, "not_supported"} - end; - _ -> - test_server:fail(Result) - end, - ?line ?t:timetrap_cancel(Timetrap), + TS0 = erlang:monotonic_time(), + Result = (catch fprof:apply(?MODULE, create_file_slow, + [DataFile, 1024], + [{file, TraceFile}, cpu_time])), + TS1 = erlang:monotonic_time(), + TestResult = + case Result of + ok -> + ok = fprof:profile(file, TraceFile), + ok = fprof:analyse(), + ok = fprof:analyse(dest, AnalysisFile), + ok = fprof:stop(), + %% + {ok, [T, P]} = parse(AnalysisFile), + io:format("~p~n~n~p~n", [P, ets:tab2list(T)]), + ok = verify(T, P), + Proc = pid_to_list(self()), + case P of + [{analysis_options, _}, + [{totals, _, Acc, _}], + [{Proc, _, undefined, _} | _]] -> + ok + end, + %% + check_own_and_acc(TraceFile,AnalysisFile), + %% + ets:delete(T), + file:delete(DataFile), + file:delete(TraceFile), + file:delete(AnalysisFile), + Acc1 = TS1 - TS0, + io:format("cpu_ts:~w, fprof:~w~n", [Acc, Acc1]), + {comment, io_lib:format("~p% cpu utilization", [100*divide(Acc,Acc1)])}; + {'EXIT', not_supported} -> + case {os:type(), os:version()} of + {{unix, sunos}, {Major, Minor, _}} + when Major >= 5, Minor >= 7 -> + ct:fail(Result); + _ -> + {skipped, "not_supported"} + end; + _ -> + ct:fail(Result) + end, TestResult. - %%%--------------------------------------------------------------------- %%% Functions to test %%%--------------------------------------------------------------------- @@ -623,14 +560,14 @@ seq_r(Start, Stop, Succ, R) -> create_file_slow(Name, N) when is_integer(N), N >= 0 -> {ok, FD} = - file:open(Name, [raw, write, delayed_write, binary]), + file:open(Name, [raw, write, delayed_write, binary]), if N > 256 -> - ok = file:write(FD, - lists:map(fun (X) -> <<X:32/unsigned>> end, - lists:seq(0, 255))), - ok = create_file_slow(FD, 256, N); + ok = file:write(FD, + lists:map(fun (X) -> <<X:32/unsigned>> end, + lists:seq(0, 255))), + ok = create_file_slow(FD, 256, N); true -> - ok = create_file_slow(FD, 0, N) + ok = create_file_slow(FD, 0, N) end, ok = file:close(FD). @@ -647,46 +584,44 @@ create_file_slow(FD, M, N) -> %%%--------------------------------------------------------------------- - verify(Tab, [{analysis_options, _}, - [{totals, Cnt, Acc, Own} | _] | Processes]) -> + [{totals, Cnt, Acc, Own} | _] | Processes]) -> Processes_1 = - lists:map( - fun ([{Proc, Cnt_P, undefined, Own_P} | _]) -> - case sum_process(Tab, Proc) of - {Proc, Cnt_P, Acc_P, Own_P} = Clocks - when Acc_P >= Own_P -> - Clocks; - Weird -> - throw({error, [?MODULE, ?LINE, Weird]}) - end - end, - Processes), + lists:map( + fun ([{Proc, Cnt_P, undefined, Own_P} | _]) -> + case sum_process(Tab, Proc) of + {Proc, Cnt_P, Acc_P, Own_P} = Clocks + when Acc_P >= Own_P -> + Clocks; + Weird -> + throw({error, [?MODULE, ?LINE, Weird]}) + end + end, + Processes), case lists:foldl( - fun ({_, Cnt_P2, Acc_P2, Own_P2}, - {totals, Cnt_T, Acc_T, Own_T}) -> - {totals, Cnt_P2+Cnt_T, Acc_P2+Acc_T, Own_P2+Own_T} - end, - {totals, 0, 0, 0}, - Processes_1) of - {totals, Cnt, Acc_T, Own} when Acc_T >= Acc -> - ok; - Weird -> - throw({error, [?MODULE, ?LINE, Weird]}) + fun ({_, Cnt_P2, Acc_P2, Own_P2}, + {totals, Cnt_T, Acc_T, Own_T}) -> + {totals, Cnt_P2+Cnt_T, Acc_P2+Acc_T, Own_P2+Own_T} + end, + {totals, 0, 0, 0}, + Processes_1) of + {totals, Cnt, Acc_T, Own} when Acc_T >= Acc -> + ok; + Weird -> + throw({error, [?MODULE, ?LINE, Weird]}) end. - sum_process(Tab, Proc) -> ets_select_fold( Tab, [{{{Proc, '_'}, '_'}, [], ['$_']}], 100, fun ({{P, MFA}, {Callers, {MFA, Cnt, Acc, Own}, Called}}, - {P, Cnt_P, Acc_P, Own_P}) when P == Proc -> - ok = verify_callers(Tab, Proc, MFA, Callers), - ok = verify_called(Tab, Proc, MFA, Called), - {P, Cnt+Cnt_P, Acc+Acc_P, Own+Own_P}; - (Weird, Clocks) -> - throw({error, [?MODULE, ?LINE, Weird, Clocks]}) + {P, Cnt_P, Acc_P, Own_P}) when P == Proc -> + ok = verify_callers(Tab, Proc, MFA, Callers), + ok = verify_called(Tab, Proc, MFA, Called), + {P, Cnt+Cnt_P, Acc+Acc_P, Own+Own_P}; + (Weird, Clocks) -> + throw({error, [?MODULE, ?LINE, Weird, Clocks]}) end, {Proc, 0, 0, 0}). @@ -695,31 +630,31 @@ verify_callers(_, _, _, []) -> verify_callers(Tab, Proc, MFA, [{Caller, Cnt, Acc, Own} | Tail]) -> Id = {Proc, Caller}, case ets:lookup(Tab, Id) of - [{Id, {_, {Caller, _, _, _}, Called}}] -> - case lists:keysearch(MFA, 1, Called) of - {value, {MFA, Cnt, Acc, Own}} -> - verify_callers(Tab, Proc, MFA, Tail); - false -> - throw({error, [?MODULE, ?LINE, MFA, Id]}) - end; - Weird -> - throw({error, [?MODULE, ?LINE, Weird]}) + [{Id, {_, {Caller, _, _, _}, Called}}] -> + case lists:keysearch(MFA, 1, Called) of + {value, {MFA, Cnt, Acc, Own}} -> + verify_callers(Tab, Proc, MFA, Tail); + false -> + throw({error, [?MODULE, ?LINE, MFA, Id]}) + end; + Weird -> + throw({error, [?MODULE, ?LINE, Weird]}) end. - + verify_called(_, _, _, []) -> ok; verify_called(Tab, Proc, MFA, [{Called, Cnt, Acc, Own} | Tail]) -> Id = {Proc, Called}, case ets:lookup(Tab, Id) of - [{Id, {Callers, {Called, _, _, _}, _}}] -> - case lists:keysearch(MFA, 1, Callers) of - {value, {MFA, Cnt, Acc, Own}} -> - verify_called(Tab, Proc, MFA, Tail); - false -> - throw({error, [?MODULE, ?LINE, MFA, Id]}) - end; - Weird -> - throw({error, [?MODULE, ?LINE, Weird]}) + [{Id, {Callers, {Called, _, _, _}, _}}] -> + case lists:keysearch(MFA, 1, Callers) of + {value, {MFA, Cnt, Acc, Own}} -> + verify_called(Tab, Proc, MFA, Tail); + false -> + throw({error, [?MODULE, ?LINE, MFA, Id]}) + end; + Weird -> + throw({error, [?MODULE, ?LINE, Weird]}) end. @@ -729,12 +664,12 @@ verify_called(Tab, Proc, MFA, [{Called, Cnt, Acc, Own} | Tail]) -> %% entries when they are read. parse(Filename) -> case file:open(Filename, [read]) of - {ok, FD} -> - Result = parse_stream(FD), - file:close(FD), - Result; - Error -> - Error + {ok, FD} -> + Result = parse_stream(FD), + file:close(FD), + Result; + Error -> + Error end. parse_stream(FD) -> @@ -743,31 +678,31 @@ parse_stream(FD) -> parse_stream(FD, Tab, R, Proc) -> case catch io:read(FD, '') of - {'EXIT', _} -> - {error, [?MODULE, ?LINE]}; - {ok, Term} -> - case parse_term(Term) of - {ok, {analysis_options, _} = Term_1} - when Proc == void -> - parse_stream(FD, Tab, [Term_1 | R], analysis_options); - {ok, [{totals, _, _, _} | _] = Term_1} - when Proc == analysis_options -> - parse_stream(FD, Tab, [Term_1 | R], totals); - {ok, [{P, _, _, _} | _] = Term_1} -> - parse_stream(FD, Tab, [Term_1 | R], P); - {ok, {_Callers, {MFA, _, _, _}, _Called} = Term_1} - when Proc == totals; is_list(Proc) -> - ets:insert(Tab, {{Proc, MFA}, Term_1}), - parse_stream(FD, Tab, R, Proc); - {ok, Term_1} -> - {error, [?MODULE, ?LINE, Term_1]}; - E -> - E - end; - eof -> - {ok, [Tab, lists:reverse(R)]}; - Error -> - Error + {'EXIT', _} -> + {error, [?MODULE, ?LINE]}; + {ok, Term} -> + case parse_term(Term) of + {ok, {analysis_options, _} = Term_1} + when Proc == void -> + parse_stream(FD, Tab, [Term_1 | R], analysis_options); + {ok, [{totals, _, _, _} | _] = Term_1} + when Proc == analysis_options -> + parse_stream(FD, Tab, [Term_1 | R], totals); + {ok, [{P, _, _, _} | _] = Term_1} -> + parse_stream(FD, Tab, [Term_1 | R], P); + {ok, {_Callers, {MFA, _, _, _}, _Called} = Term_1} + when Proc == totals; is_list(Proc) -> + ets:insert(Tab, {{Proc, MFA}, Term_1}), + parse_stream(FD, Tab, R, Proc); + {ok, Term_1} -> + {error, [?MODULE, ?LINE, Term_1]}; + E -> + E + end; + eof -> + {ok, [Tab, lists:reverse(R)]}; + Error -> + Error end. parse_term({Callers, Func, Called}) @@ -777,10 +712,10 @@ parse_term({Callers, Func, Called}) Called_1 = lists:map(fun parse_clocks/1, Called), Result = {Callers_1, Func_1, Called_1}, case chk_invariant(Result) of - ok -> - {ok, Result}; - Error -> - Error + ok -> + {ok, Result}; + Error -> + Error end; parse_term([{_, _, _, _} = Clocks | Tail]) -> {ok, [parse_clocks(Clocks) | Tail]}; @@ -798,41 +733,41 @@ parse_clocks(Clocks) -> chk_invariant({Callers, {MFA, Cnt, Acc, Own}, Called} = Term) -> {_, Callers_Cnt, Callers_Acc, Callers_Own} = Callers_Sum = sum(Callers), -% {_, Called_Cnt, Called_Acc, Called_Own} = Called_Sum = sum(Called), + % {_, Called_Cnt, Called_Acc, Called_Own} = Called_Sum = sum(Called), case {MFA, - lists:keymember(suspend, 1, Callers), - lists:keymember(garbage_collect, 1, Callers), - Called} of - {suspend, false, _, []} -> - ok; - {suspend, _, _, _} = Weird -> - {error, [?MODULE, ?LINE, Weird, Term]}; - {garbage_collect, false, false, []} -> - ok; - {garbage_collect, false, false, [{suspend, _, _, _}]} -> - ok; - {garbage_collect, _, _, _} = Weird -> - {error, [?MODULE, ?LINE, Weird, Term]}; - {undefined, false, false, _} - when Callers == [], Cnt == 0, Acc == 0, Own == 0 -> - ok; - {undefined, _, _, _} = Weird -> - {error, [?MODULE, ?LINE, Weird, Term]}; - {_, _, _, _} -> - case chk_self_call(Term) of - true when Callers_Cnt /= Cnt; Callers_Acc /= Acc; - Callers_Own /= Own -> - {error, [?MODULE, ?LINE, Callers_Sum, Term]}; -% true when Called_Acc + Own /= Acc -> -% io:format("WARNING: ~p:~p, ~p, ~p.~n", -% [?MODULE, ?LINE, Term, Called_Sum]), -% {error, [?MODULE, ?LINE, Term, Called_Sum]}; -% ok; - true -> - ok; - false -> - {error, [?MODULE, ?LINE, Term]} - end + lists:keymember(suspend, 1, Callers), + lists:keymember(garbage_collect, 1, Callers), + Called} of + {suspend, false, _, []} -> + ok; + {suspend, _, _, _} = Weird -> + {error, [?MODULE, ?LINE, Weird, Term]}; + {garbage_collect, false, false, []} -> + ok; + {garbage_collect, false, false, [{suspend, _, _, _}]} -> + ok; + {garbage_collect, _, _, _} = Weird -> + {error, [?MODULE, ?LINE, Weird, Term]}; + {undefined, false, false, _} + when Callers == [], Cnt == 0, Acc == 0, Own == 0 -> + ok; + {undefined, _, _, _} = Weird -> + {error, [?MODULE, ?LINE, Weird, Term]}; + {_, _, _, _} -> + case chk_self_call(Term) of + true when Callers_Cnt /= Cnt; Callers_Acc /= Acc; + Callers_Own /= Own -> + {error, [?MODULE, ?LINE, Callers_Sum, Term]}; + % true when Called_Acc + Own /= Acc -> + % io:format("WARNING: ~p:~p, ~p, ~p.~n", + % [?MODULE, ?LINE, Term, Called_Sum]), + % {error, [?MODULE, ?LINE, Term, Called_Sum]}; + % ok; + true -> + ok; + false -> + {error, [?MODULE, ?LINE, Term]} + end end. ts_sub({A, B, C}, {A0, B0, C0}) -> @@ -840,28 +775,28 @@ ts_sub({A, B, C}, {A0, B0, C0}) -> sum(Funcs) -> {sum, _Cnt, _Acc, _Own} = - lists:foldl( - fun ({_, C1, A1, O1}, {sum, C2, A2, O2}) -> - {sum, C1+C2, A1+A2, O1+O2} - end, - {sum, 0, 0, 0}, - Funcs). + lists:foldl( + fun ({_, C1, A1, O1}, {sum, C2, A2, O2}) -> + {sum, C1+C2, A1+A2, O1+O2} + end, + {sum, 0, 0, 0}, + Funcs). chk_self_call({Callers, {MFA, _Cnt, _Acc, _Own}, Called}) -> case lists:keysearch(MFA, 1, Callers) of - false -> - true; - {value, {MFA, C, 0, O}} -> - case lists:keysearch(MFA, 1, Called) of - false -> - false; - {value, {MFA, C, 0, O}} -> - true; - {value, _} -> - false - end; - {value, _} -> - false + false -> + true; + {value, {MFA, C, 0, O}} -> + case lists:keysearch(MFA, 1, Called) of + false -> + false; + {value, {MFA, C, 0, O}} -> + true; + {value, _} -> + false + end; + {value, _} -> + false end. @@ -879,9 +814,8 @@ ets_select_fold_1('$end_of_table', _, Acc) -> Acc; ets_select_fold_1({Matches, Continuation}, Fun, Acc) -> ets_select_fold_1(ets:select(Continuation), - Fun, - lists:foldl(Fun, Acc, Matches)). - + Fun, + lists:foldl(Fun, Acc, Matches)). % ets_select_foreach(Table, MatchSpec, Limit, Fun) -> @@ -910,7 +844,7 @@ check_own_and_acc(TraceFile, AnalysisFile) -> check_own_and_acc(TraceFile, AnalysisFile, HandlerFun) -> dbg:trace_client(file,TraceFile,{HandlerFun,{init,self()}}), receive {result,Result} -> - compare(Result,get_own_and_acc_from_analysis(AnalysisFile)) + compare(Result,get_own_and_acc_from_analysis(AnalysisFile)) end. %% handle_trace_traced(Trace, Msg) -> @@ -924,21 +858,21 @@ handle_trace(Trace,{init,Parent}) -> handle_trace({trace_ts,Pid,in,MFA,TS},P) -> ?dbg("~p",[{{in,Pid,MFA},get(Pid)}]), case get(Pid) of - [suspend|[suspend|_]=NewStack] -> - T = ts_sub(TS,get({Pid,last_ts})), - update_acc(Pid,NewStack,T), - put(Pid,NewStack); - [suspend|NewStack] = Stack -> - T = ts_sub(TS,get({Pid,last_ts})), - update_acc(Pid,Stack,T), - put(Pid,NewStack); - [] -> - put(Pid,[MFA]), - insert(Pid,MFA); - undefined -> - put(first_ts,TS), - put(Pid,[MFA]), - insert(Pid,MFA) + [suspend|[suspend|_]=NewStack] -> + T = ts_sub(TS,get({Pid,last_ts})), + update_acc(Pid,NewStack,T), + put(Pid,NewStack); + [suspend|NewStack] = Stack -> + T = ts_sub(TS,get({Pid,last_ts})), + update_acc(Pid,Stack,T), + put(Pid,NewStack); + [] -> + put(Pid,[MFA]), + insert(Pid,MFA); + undefined -> + put(first_ts,TS), + put(Pid,[MFA]), + insert(Pid,MFA) end, put({Pid,last_ts},TS), P; @@ -946,17 +880,17 @@ handle_trace({trace_ts,Pid,out,_MfaOrZero,TS},P) -> ?dbg("~p",[{{out,Pid,_MfaOrZero},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), case get(Pid) of - [suspend|S] = Stack -> - update_acc(Pid,S,T), - put(Pid,[suspend|Stack]); - [MFA|_] = Stack -> - insert(Pid,suspend), - update_own(Pid,MFA,T), - update_acc(Pid,Stack,T), - put(Pid,[suspend|Stack]); - [] -> - insert(Pid,suspend), - put(Pid,[suspend]) + [suspend|S] = Stack -> + update_acc(Pid,S,T), + put(Pid,[suspend|Stack]); + [MFA|_] = Stack -> + insert(Pid,suspend), + update_own(Pid,MFA,T), + update_acc(Pid,Stack,T), + put(Pid,[suspend|Stack]); + [] -> + insert(Pid,suspend), + put(Pid,[suspend]) end, put({Pid,last_ts},TS), P; @@ -964,26 +898,26 @@ handle_trace({trace_ts,Pid,call,MFA,{cp,Caller},TS},P) -> ?dbg("~p",[{{call,Pid,MFA},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), case get(Pid) of - [MFA|_] = Stack -> - %% recursive - update_own(Pid,MFA,T), - update_acc(Pid,Stack,T); - [CallingMFA|_] = Stack when Caller==undefined -> - insert(Pid,MFA), - update_own(Pid,CallingMFA,T), - update_acc(Pid,Stack,T), - put(Pid,[MFA|Stack]); - [] when Caller==undefined -> - insert(Pid,MFA), - insert(Pid,MFA), - put(Pid,[MFA]); - Stack0 -> - Stack = [CallingMFA|_] = insert_caller(Caller,Stack0,[]), - insert(Pid,MFA), - insert(Pid,Caller), - update_own(Pid,CallingMFA,T), - update_acc(Pid,Stack,T), - put(Pid,[MFA|Stack]) + [MFA|_] = Stack -> + %% recursive + update_own(Pid,MFA,T), + update_acc(Pid,Stack,T); + [CallingMFA|_] = Stack when Caller==undefined -> + insert(Pid,MFA), + update_own(Pid,CallingMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[MFA|Stack]); + [] when Caller==undefined -> + insert(Pid,MFA), + insert(Pid,MFA), + put(Pid,[MFA]); + Stack0 -> + Stack = [CallingMFA|_] = insert_caller(Caller,Stack0,[]), + insert(Pid,MFA), + insert(Pid,Caller), + update_own(Pid,CallingMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[MFA|Stack]) end, put({Pid,last_ts},TS), P; @@ -991,59 +925,91 @@ handle_trace({trace_ts,Pid,return_to,MFA,TS},P) -> ?dbg("~p",[{{return_to,Pid,MFA},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), case get(Pid) of - [MFA|_] = Stack -> - %% recursive - update_own(Pid,MFA,T), - update_acc(Pid,Stack,T), - put(Pid,Stack); - [ReturnFromMFA,MFA|RestOfStack] = Stack -> - update_own(Pid,ReturnFromMFA,T), - update_acc(Pid,Stack,T), - put(Pid,[MFA|RestOfStack]); - [ReturnFromMFA|RestOfStack] = Stack -> - update_own(Pid,ReturnFromMFA,T), - update_acc(Pid,Stack,T), - case find_return_to(MFA,RestOfStack) of - [] when MFA==undefined -> - put(Pid,[]); - [] -> - insert(Pid,MFA), - put(Pid,[MFA]); - NewStack -> - put(Pid,NewStack) - end + [MFA|_] = Stack -> + %% recursive + update_own(Pid,MFA,T), + update_acc(Pid,Stack,T), + put(Pid,Stack); + [ReturnFromMFA,MFA|RestOfStack] = Stack -> + update_own(Pid,ReturnFromMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[MFA|RestOfStack]); + [ReturnFromMFA|RestOfStack] = Stack -> + update_own(Pid,ReturnFromMFA,T), + update_acc(Pid,Stack,T), + case find_return_to(MFA,RestOfStack) of + [] when MFA==undefined -> + put(Pid,[]); + [] -> + insert(Pid,MFA), + put(Pid,[MFA]); + NewStack -> + put(Pid,NewStack) + end end, put({Pid,last_ts},TS), P; -handle_trace({trace_ts,Pid,gc_start,_,TS},P) -> - ?dbg("~p",[{{gc_start,Pid},get(Pid)}]), +handle_trace({trace_ts,Pid,gc_minor_start,_,TS},P) -> + ?dbg("~p",[{{gc_minor_start,Pid},get(Pid)}]), case get(Pid) of - [suspend|_] = Stack -> - T = ts_sub(TS,get({Pid,last_ts})), - insert(Pid,garbage_collect), - update_acc(Pid,Stack,T), - put(Pid,[garbage_collect|Stack]); - [CallingMFA|_] = Stack -> - T = ts_sub(TS,get({Pid,last_ts})), - insert(Pid,garbage_collect), - update_own(Pid,CallingMFA,T), - update_acc(Pid,Stack,T), - put(Pid,[garbage_collect|Stack]); - undefined -> - put(first_ts,TS), - put(Pid,[garbage_collect]), - insert(Pid,garbage_collect) + [suspend|_] = Stack -> + T = ts_sub(TS,get({Pid,last_ts})), + insert(Pid,garbage_collect), + update_acc(Pid,Stack,T), + put(Pid,[garbage_collect|Stack]); + [CallingMFA|_] = Stack -> + T = ts_sub(TS,get({Pid,last_ts})), + insert(Pid,garbage_collect), + update_own(Pid,CallingMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[garbage_collect|Stack]); + undefined -> + put(first_ts,TS), + put(Pid,[garbage_collect]), + insert(Pid,garbage_collect) end, put({Pid,last_ts},TS), P; -handle_trace({trace_ts,Pid,gc_end,_,TS},P) -> - ?dbg("~p",[{{gc_end,Pid},get(Pid)}]), +handle_trace({trace_ts,Pid,gc_major_start,_,TS},P) -> + ?dbg("~p",[{{gc_minor_start,Pid},get(Pid)}]), + case get(Pid) of + [suspend|_] = Stack -> + T = ts_sub(TS,get({Pid,last_ts})), + insert(Pid,garbage_collect), + update_acc(Pid,Stack,T), + put(Pid,[garbage_collect|Stack]); + [CallingMFA|_] = Stack -> + T = ts_sub(TS,get({Pid,last_ts})), + insert(Pid,garbage_collect), + update_own(Pid,CallingMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[garbage_collect|Stack]); + undefined -> + put(first_ts,TS), + put(Pid,[garbage_collect]), + insert(Pid,garbage_collect) + end, + put({Pid,last_ts},TS), + P; +handle_trace({trace_ts,Pid,gc_minor_end,_,TS},P) -> + ?dbg("~p",[{{gc_minor_end,Pid},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), case get(Pid) of - [garbage_collect|RestOfStack] = Stack -> - update_own(Pid,garbage_collect,T), - update_acc(Pid,Stack,T), - put(Pid,RestOfStack) + [garbage_collect|RestOfStack] = Stack -> + update_own(Pid,garbage_collect,T), + update_acc(Pid,Stack,T), + put(Pid,RestOfStack) + end, + put({Pid,last_ts},TS), + P; +handle_trace({trace_ts,Pid,gc_major_end,_,TS},P) -> + ?dbg("~p",[{{gc_major_end,Pid},get(Pid)}]), + T = ts_sub(TS,get({Pid,last_ts})), + case get(Pid) of + [garbage_collect|RestOfStack] = Stack -> + update_own(Pid,garbage_collect,T), + update_acc(Pid,Stack,T), + put(Pid,RestOfStack) end, put({Pid,last_ts},TS), P; @@ -1051,27 +1017,45 @@ handle_trace({trace_ts,Pid,spawn,NewPid,{M,F,Args},TS},P) -> MFA = {M,F,length(Args)}, ?dbg("~p",[{{spawn,Pid,NewPid,MFA},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), - put({NewPid,last_ts},TS), - put(NewPid,[suspend,MFA]), - insert(NewPid,suspend), - insert(NewPid,MFA), + case get(NewPid) of + undefined -> + put({NewPid,last_ts},TS), + put(NewPid,[suspend,MFA]), + insert(NewPid,suspend), + insert(NewPid,MFA); + _Else -> + ok + end, case get(Pid) of - [SpawningMFA|_] = Stack -> - update_own(Pid,SpawningMFA,T), - update_acc(Pid,Stack,T) + [SpawningMFA|_] = Stack -> + update_own(Pid,SpawningMFA,T), + update_acc(Pid,Stack,T) end, put({Pid,last_ts},TS), P; +handle_trace({trace_ts,NewPid,spawned,Pid,{M,F,Args},TS},P) -> + MFA = {M,F,length(Args)}, + ?dbg("~p",[{{spawned,NewPid,Pid,MFA},get(NewPid)}]), + case get(NewPid) of + undefined -> + put({NewPid,last_ts},TS), + put(NewPid,[suspend,MFA]), + insert(NewPid,suspend), + insert(NewPid,MFA); + _Else -> + ok + end, + P; handle_trace({trace_ts,Pid,exit,_Reason,TS},P) -> ?dbg("~p",[{{exit,Pid,_Reason},get(Pid)}]), T = ts_sub(TS,get({Pid,last_ts})), case get(Pid) of - [DyingMFA|_] = Stack -> - update_own(Pid,DyingMFA,T), - update_acc(Pid,Stack,T), - put(Pid,[]); - [] -> - ok + [DyingMFA|_] = Stack -> + update_own(Pid,DyingMFA,T), + update_acc(Pid,Stack,T), + put(Pid,[]); + [] -> + ok end, put({Pid,last_ts},TS), P; @@ -1089,6 +1073,7 @@ handle_trace(end_of_trace,P) -> P ! {result,[{totals,TotAcc,TotOwn}|ProcOwns]++Result}, P; handle_trace(Other,_P) -> + ct:log("Got unexpected trace message: ~p",[Other]), exit({unexpected,Other}). find_return_to(MFA,[MFA|_]=Stack) -> @@ -1107,10 +1092,10 @@ insert_caller(MFA,[],Result) -> insert(Pid,MFA) -> case ets:member(fprof_verify_tab,{Pid,MFA}) of - false -> - ets:insert(fprof_verify_tab,{{Pid,MFA},0,0}); - true -> - ok + false -> + ets:insert(fprof_verify_tab,{{Pid,MFA},0,0}); + true -> + ok end. update_own(Pid,MFA,T) -> @@ -1118,11 +1103,11 @@ update_own(Pid,MFA,T) -> update_acc(Pid,[MFA|Rest],T) -> case lists:member(MFA,Rest) of - true -> - %% Only charge one time for recursive functions - ok; - false -> - ets:update_counter(fprof_verify_tab,{Pid,MFA},{2,T}) + true -> + %% Only charge one time for recursive functions + ok; + false -> + ets:update_counter(fprof_verify_tab,{Pid,MFA},{2,T}) end, update_acc(Pid,Rest,T); update_acc(_Pid,[],_T) -> @@ -1140,63 +1125,63 @@ get_last_ts([],Last) -> get_proc_owns([{{Pid,_MFA},_Acc,Own}|Rest],Result,Sum) -> NewResult = - case lists:keysearch(Pid,1,Result) of - {value,{Pid,undefined,PidOwn}} -> - lists:keyreplace(Pid,1,Result,{Pid,undefined,PidOwn+Own}); - false -> - [{Pid,undefined,Own}|Result] + case lists:keysearch(Pid,1,Result) of + {value,{Pid,undefined,PidOwn}} -> + lists:keyreplace(Pid,1,Result,{Pid,undefined,PidOwn+Own}); + false -> + [{Pid,undefined,Own}|Result] end, get_proc_owns(Rest,NewResult,Sum+Own); get_proc_owns([],Result,Sum) -> {Sum,Result}. - + compare([X|Rest],FprofResult) -> FprofResult1 = - case lists:member(X,FprofResult) of - true -> - ?dbg("~p",[X]), - lists:delete(X,FprofResult); - false -> - case lists:keysearch(element(1,X),1,FprofResult) of - {value,Fprof} -> - put(compare_error,true), - io:format("Error: Different values\n" - "Fprof: ~p\n" - "Simulator: ~p",[Fprof,X]), - lists:delete(Fprof,FprofResult); - false -> - put(compare_error,true), - io:format("Error: Missing in fprof: ~p",[X]), - FprofResult - end - end, + case lists:member(X,FprofResult) of + true -> + ?dbg("~p",[X]), + lists:delete(X,FprofResult); + false -> + case lists:keysearch(element(1,X),1,FprofResult) of + {value,Fprof} -> + put(compare_error,true), + io:format("Error: Different values\n" + "Fprof: ~p\n" + "Simulator: ~p",[Fprof,X]), + lists:delete(Fprof,FprofResult); + false -> + put(compare_error,true), + io:format("Error: Missing in fprof: ~p",[X]), + FprofResult + end + end, compare(Rest,FprofResult1); compare([],Rest) -> case {remove_undefined(Rest,[]),get(compare_error)} of - {[],undefined} -> ok; - {Error,_} -> - case Error of - [] -> ok; - _ -> io:format("\nMissing in simulator results:\n~p\n",[Error]) - end, - ?t:fail({error,mismatch_between_simulator_and_fprof}) + {[],undefined} -> ok; + {Error,_} -> + case Error of + [] -> ok; + _ -> io:format("\nMissing in simulator results:\n~p\n",[Error]) + end, + ct:fail({error,mismatch_between_simulator_and_fprof}) end. - + remove_undefined([{{_Pid,undefined},_,_}|Rest],Result) -> remove_undefined(Rest,Result); remove_undefined([X|Rest],Result) -> remove_undefined(Rest,[X|Result]); remove_undefined([],Result) -> Result. - + get_own_and_acc_from_analysis(Log) -> case file:consult(Log) of - {ok,[_Options,[{totals,_,TotAcc,TotOwn}]|Rest]} -> - get_own_and_acc(undefined,Rest, - [{totals,m1000(TotAcc),m1000(TotOwn)}]); - Error -> - exit({error,{cant_open,Log,Error}}) + {ok,[_Options,[{totals,_,TotAcc,TotOwn}]|Rest]} -> + get_own_and_acc(undefined,Rest, + [{totals,m1000(TotAcc),m1000(TotOwn)}]); + Error -> + exit({error,{cant_open,Log,Error}}) end. get_own_and_acc(_,[[{PidStr,_,Acc,Own}|_]|Rest],Result) -> @@ -1212,3 +1197,5 @@ m1000(undefined) -> m1000(X) -> round(X*1000). +divide(_,0) -> inf; +divide(A,B) -> A / B. diff --git a/lib/tools/test/ignore_cores.erl b/lib/tools/test/ignore_cores.erl index e40b91392c..25dce346b9 100644 --- a/lib/tools/test/ignore_cores.erl +++ b/lib/tools/test/ignore_cores.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2008-2010. All Rights Reserved. +%% Copyright Ericsson AB 2008-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -53,7 +53,7 @@ init(Config) -> fini(Config) -> #ignore_cores{org_cwd = OrgCWD, org_path = OrgPath, - org_pwd_env = OrgPWD} = ?config(ignore_cores, Config), + org_pwd_env = OrgPWD} = proplists:get_value(ignore_cores, Config), ok = file:set_cwd(OrgCWD), true = code:set_path(OrgPath), case OrgPWD of @@ -70,10 +70,10 @@ setup(Suite, Testcase, Config, SetCwd) when is_atom(Suite), is_list(Config) -> #ignore_cores{org_cwd = OrgCWD, org_path = OrgPath, - org_pwd_env = OrgPWD} = ?config(ignore_cores, Config), + org_pwd_env = OrgPWD} = proplists:get_value(ignore_cores, Config), Path = lists:map(fun (".") -> OrgCWD; (Dir) -> Dir end, OrgPath), true = code:set_path(Path), - PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), IgnDir = filename:join([PrivDir, atom_to_list(Suite) ++ "_" @@ -94,7 +94,7 @@ setup(Suite, Testcase, Config, SetCwd) when is_atom(Suite), end, ok = file:write_file(filename:join([IgnDir, "ignore_core_files"]), <<>>), %% cores are dumped in /cores on MacOS X - CoresDir = case {?t:os_type(), filelib:is_dir("/cores")} of + CoresDir = case {os:type(), filelib:is_dir("/cores")} of {{unix,darwin}, true} -> filelib:fold_files("/cores", "^core.*$", @@ -119,7 +119,7 @@ restore(Config) -> org_path = OrgPath, org_pwd_env = OrgPWD, ign_dir = IgnDir, - cores_dir = CoresDir} = ?config(ignore_cores, Config), + cores_dir = CoresDir} = proplists:get_value(ignore_cores, Config), try case CoresDir of false -> @@ -155,5 +155,5 @@ restore(Config) -> dir(Config) -> - #ignore_cores{ign_dir = Dir} = ?config(ignore_cores, Config), + #ignore_cores{ign_dir = Dir} = proplists:get_value(ignore_cores, Config), Dir. diff --git a/lib/tools/test/instrument_SUITE.erl b/lib/tools/test/instrument_SUITE.erl index 773d805cd0..f37d28c277 100644 --- a/lib/tools/test/instrument_SUITE.erl +++ b/lib/tools/test/instrument_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1998-2011. All Rights Reserved. +%% Copyright Ericsson AB 1998-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -19,133 +19,99 @@ %% -module(instrument_SUITE). --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2, - init_per_testcase/2,end_per_testcase/2]). - +-export([all/0, suite/0]). -export(['+Mim true'/1, '+Mis true'/1]). -include_lib("common_test/include/ct.hrl"). -init_per_testcase(_Case, Config) -> - ?line Dog=?t:timetrap(10000), - [{watchdog, Dog}|Config]. - -end_per_testcase(_Case, Config) -> - Dog=?config(watchdog, Config), - ?t:timetrap_cancel(Dog), - ok. - -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{seconds,10}}]. all() -> ['+Mim true', '+Mis true']. -groups() -> - []. - -init_per_suite(Config) -> - Config. - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - -'+Mim true'(doc) -> ["Check that memory data can be read and processed"]; -'+Mim true'(suite) -> []; +%% Check that memory data can be read and processed '+Mim true'(Config) when is_list(Config) -> - ?line Node = start_slave("+Mim true"), - ?line MD = rpc:call(Node, instrument, memory_data, []), - ?line [{total,[{sizes,S1,S2,S3},{blocks,B1,B2,B3}]}] + Node = start_slave("+Mim true"), + MD = rpc:call(Node, instrument, memory_data, []), + [{total,[{sizes,S1,S2,S3},{blocks,B1,B2,B3}]}] = rpc:call(Node, instrument, memory_status, [total]), - ?line stop_slave(Node), - ?line true = S1 =< S2, - ?line true = S2 =< S3, - ?line true = B1 =< B2, - ?line true = B2 =< B3, - ?line MDS = instrument:sort(MD), - ?line {Low, High} = instrument:mem_limits(MDS), - ?line true = Low < High, - ?line {_, AL} = MDS, - ?line SumBlocks = instrument:sum_blocks(MD), - ?line case SumBlocks of - N when is_integer(N) -> - ?line N = lists:foldl(fun ({_,_,Size,_}, Sum) -> - Size+Sum - end, - 0, - AL), - ?line N =< S3; - Other -> - ?line ?t:fail(Other) - end, - ?line lists:foldl( - fun ({TDescr,Addr,Size,Proc}, MinAddr) -> - ?line true = TDescr /= invalid_type, - ?line true = is_integer(TDescr), - ?line true = is_integer(Addr), - ?line true = is_integer(Size), - ?line true = Addr >= MinAddr, - ?line case Proc of - {0, Number, Serial} -> - ?line true = is_integer(Number), - ?line true = is_integer(Serial); - undefined -> - ok; - BadProc -> - ?line ?t:fail({badproc, BadProc}) - end, - ?line NextMinAddr = Addr+Size, - ?line true = NextMinAddr =< High, - ?line NextMinAddr - end, - Low, - AL), - ?line {_, DAL} = instrument:descr(MDS), - ?line lists:foreach( - fun ({TDescr,_,_,Proc}) -> - ?line true = TDescr /= invalid_type, - ?line true = is_atom(TDescr) orelse is_list(TDescr), - ?line true = is_pid(Proc) orelse Proc == undefined - end, - DAL), - ?line ASL = lists:map(fun ({_,A,S,_}) -> {A,S} end, AL), - ?line ASL = lists:map(fun ({_,A,S,_}) -> {A,S} end, DAL), - ?line instrument:holes(MDS), - ?line {comment, - "total status - sum of blocks = " ++ integer_to_list(S1-SumBlocks)}. - -'+Mis true'(doc) -> ["Check that memory data can be read and processed"]; -'+Mis true'(suite) -> []; + stop_slave(Node), + true = S1 =< S2, + true = S2 =< S3, + true = B1 =< B2, + true = B2 =< B3, + MDS = instrument:sort(MD), + {Low, High} = instrument:mem_limits(MDS), + true = Low < High, + {_, AL} = MDS, + SumBlocks = instrument:sum_blocks(MD), + case SumBlocks of + N when is_integer(N) -> + N = lists:foldl(fun ({_,_,Size,_}, Sum) -> + Size+Sum + end, 0, AL), + true = N =< S3; + Other -> + ct:fail(Other) + end, + lists:foldl( + fun ({TDescr,Addr,Size,Proc}, MinAddr) -> + true = TDescr /= invalid_type, + true = is_integer(TDescr), + true = is_integer(Addr), + true = is_integer(Size), + true = Addr >= MinAddr, + case Proc of + {0, Number, Serial} -> + true = is_integer(Number), + true = is_integer(Serial); + undefined -> + ok; + BadProc -> + ct:fail({badproc, BadProc}) + end, + NextMinAddr = Addr+Size, + true = NextMinAddr =< High, + NextMinAddr + end, Low, AL), + {_, DAL} = instrument:descr(MDS), + lists:foreach( + fun ({TDescr,_,_,Proc}) -> + true = TDescr /= invalid_type, + true = is_atom(TDescr) orelse is_list(TDescr), + true = is_pid(Proc) orelse Proc == undefined + end, DAL), + ASL = lists:map(fun ({_,A,S,_}) -> {A,S} end, AL), + ASL = lists:map(fun ({_,A,S,_}) -> {A,S} end, DAL), + instrument:holes(MDS), + {comment, "total status - sum of blocks = " ++ integer_to_list(S1-SumBlocks)}. + +%% Check that memory data can be read and processed '+Mis true'(Config) when is_list(Config) -> - ?line Node = start_slave("+Mis true"), - ?line [{total,[{sizes,S1,S2,S3},{blocks,B1,B2,B3}]}] + Node = start_slave("+Mis true"), + [{total,[{sizes,S1,S2,S3},{blocks,B1,B2,B3}]}] = rpc:call(Node, instrument, memory_status, [total]), - ?line true = S1 =< S2, - ?line true = S2 =< S3, - ?line true = B1 =< B2, - ?line true = B2 =< B3, - ?line true = is_list(rpc:call(Node,instrument,memory_status,[allocators])), - ?line true = is_list(rpc:call(Node,instrument,memory_status,[classes])), - ?line true = is_list(rpc:call(Node,instrument,memory_status,[types])), - ?line ok. + true = S1 =< S2, + true = S2 =< S3, + true = B1 =< B2, + true = B2 =< B3, + true = is_list(rpc:call(Node,instrument,memory_status,[allocators])), + true = is_list(rpc:call(Node,instrument,memory_status,[classes])), + true = is_list(rpc:call(Node,instrument,memory_status,[types])), + ok. start_slave(Args) -> - ?line {A, B, C} = now(), - ?line MicroSecs = A*1000000000000 + B*1000000 + C, - ?line Name = "instr_" ++ integer_to_list(MicroSecs), - ?line Pa = filename:dirname(code:which(?MODULE)), - ?line {ok, Node} = ?t:start_node(list_to_atom(Name), - slave, - [{args, "-pa " ++ Pa ++ " " ++ Args}]), - ?line Node. + MicroSecs = erlang:monotonic_time(), + Name = "instr" ++ integer_to_list(MicroSecs), + Pa = filename:dirname(code:which(?MODULE)), + {ok, Node} = test_server:start_node(list_to_atom(Name), + slave, + [{args, "-pa " ++ Pa ++ " " ++ Args}]), + Node. stop_slave(Node) -> - ?line true = ?t:stop_node(Node). + true = test_server:stop_node(Node). diff --git a/lib/tools/test/lcnt_SUITE.erl b/lib/tools/test/lcnt_SUITE.erl index 47b8031bee..d39a5deeab 100644 --- a/lib/tools/test/lcnt_SUITE.erl +++ b/lib/tools/test/lcnt_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2010-2011. All Rights Reserved. +%% Copyright Ericsson AB 2010-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -22,56 +22,36 @@ -include_lib("common_test/include/ct.hrl"). %% Test server specific exports --export([all/0, suite/0,groups/0,init_per_group/2,end_per_group/2]). --export([init_per_suite/1, end_per_suite/1]). +-export([all/0, suite/0]). -export([init_per_testcase/2, end_per_testcase/2]). %% Test cases --export([ - t_load/1, - t_conflicts/1, - t_locations/1, - t_swap_keys/1 - ]). - -%% Default timetrap timeout (set in init_per_testcase) --define(default_timeout, ?t:minutes(4)). - -init_per_suite(Config) when is_list(Config) -> - Config. - -end_per_suite(Config) when is_list(Config) -> - Config. +-export([t_load/1, + t_conflicts/1, + t_locations/1, + t_swap_keys/1]). init_per_testcase(_Case, Config) -> - Dog = ?t:timetrap(?default_timeout), - [{watchdog,Dog} | Config]. + Config. -end_per_testcase(_Case, Config) -> - Dog = ?config(watchdog, Config), - ?t:timetrap_cancel(Dog), +end_per_testcase(_Case, _Config) -> catch lcnt:stop(), ok. -suite() -> [{ct_hooks,[ts_install_cth]}]. - -all() -> [t_load, t_conflicts, t_locations, t_swap_keys]. - -groups() -> []. - -init_per_group(_GroupName, Config) -> Config. - -end_per_group(_GroupName, Config) -> Config. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{minutes,4}}]. +all() -> + [t_load, t_conflicts, t_locations, t_swap_keys]. %%---------------------------------------------------------------------- %% Tests %%---------------------------------------------------------------------- -t_load(suite) -> []; -t_load(doc) -> ["Load data from file."]; +%% Load data from file. t_load(Config) when is_list(Config) -> - Path = ?config(data_dir, Config), + Path = proplists:get_value(data_dir, Config), Files = [filename:join([Path,"big_bang_40.lcnt"]), filename:join([Path,"ehb_3_3_hist.lcnt"])], ok = t_load_file(Files), @@ -84,10 +64,9 @@ t_load_file([File|Files]) -> ok = lcnt:stop(), t_load_file(Files). -t_conflicts(suite) -> []; -t_conflicts(doc) -> ["API: conflicts"]; +%% API: conflicts t_conflicts(Config) when is_list(Config) -> - Path = ?config(data_dir, Config), + Path = proplists:get_value(data_dir, Config), Files = [filename:join([Path,"big_bang_40.lcnt"]), filename:join([Path,"ehb_3_3_hist.lcnt"])], ok = t_conflicts_file(Files), @@ -118,10 +97,9 @@ test_conflicts_opts([Opt|Opts]) -> ok = lcnt:conflicts(Opt), test_conflicts_opts(Opts). -t_locations(suite) -> []; -t_locations(doc) -> ["API: locations"]; +%% API: locations t_locations(Config) when is_list(Config) -> - Path = ?config(data_dir, Config), + Path = proplists:get_value(data_dir, Config), Files = [filename:join([Path,"big_bang_40.lcnt"]), filename:join([Path,"ehb_3_3_hist.lcnt"])], ok = t_locations_file(Files), @@ -151,10 +129,9 @@ test_locations_opts([Opt|Opts]) -> ok = lcnt:locations(Opt), test_locations_opts(Opts). -t_swap_keys(suite) -> []; -t_swap_keys(doc) -> ["Test interchanging port/process id with class"]; +%% Test interchanging port/process id with class t_swap_keys(Config) when is_list(Config) -> - Path = ?config(data_dir, Config), + Path = proplists:get_value(data_dir, Config), Files = [filename:join([Path,"big_bang_40.lcnt"]), filename:join([Path,"ehb_3_3_hist.lcnt"])], ok = t_swap_keys_file(Files), @@ -169,12 +146,3 @@ t_swap_keys_file([File|Files]) -> ok = lcnt:conflicts(), ok = lcnt:stop(), t_swap_keys_file(Files). - - -%%---------------------------------------------------------------------- -%% Auxiliary tests -%%---------------------------------------------------------------------- - -%%---------------------------------------------------------------------- -%% Auxiliary -%%---------------------------------------------------------------------- diff --git a/lib/tools/test/make_SUITE.erl b/lib/tools/test/make_SUITE.erl index fdcc310df1..e6284db8b8 100644 --- a/lib/tools/test/make_SUITE.erl +++ b/lib/tools/test/make_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1996-2011. All Rights Reserved. +%% Copyright Ericsson AB 1996-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -20,10 +20,10 @@ -module(make_SUITE). -export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2, make_all/1, make_files/1]). + init_per_group/2,end_per_group/2, make_all/1, make_files/1]). -export([otp_6057_init/1, - otp_6057_a/1, otp_6057_b/1, otp_6057_c/1, - otp_6057_end/1]). + otp_6057_a/1, otp_6057_b/1, otp_6057_c/1, + otp_6057_end/1]). -include_lib("common_test/include/ct.hrl"). @@ -44,7 +44,7 @@ all() -> groups() -> [{otp_6057,[],[otp_6057_a, otp_6057_b, - otp_6057_c]}]. + otp_6057_c]}]. init_per_suite(Config) -> Config. @@ -61,52 +61,50 @@ end_per_group(_GroupName, Config) -> test_files() -> ["test1", "test2", "test3", "test4"]. -make_all(suite) -> []; make_all(Config) when is_list(Config) -> - ?line Current = prepare_data_dir(Config), - ?line up_to_date = make:all(), - ?line ok = ensure_exists(test_files()), - ?line ok = ensure_exists(["test5"],".S"), % Emakefile: [{test5,['S']} - ?line file:set_cwd(Current), - ?line ensure_no_messages(), + Current = prepare_data_dir(Config), + up_to_date = make:all(), + ok = ensure_exists(test_files()), + ok = ensure_exists(["test5"],".S"), % Emakefile: [{test5,['S']} + file:set_cwd(Current), + ensure_no_messages(), ok. -make_files(suite) -> []; make_files(Config) when is_list(Config) -> - ?line Current = prepare_data_dir(Config), + Current = prepare_data_dir(Config), %% Make files that exist. - ?line Files = [test1, test2], - ?line up_to_date = make:files(Files), % ok files - ?line ok = ensure_exists(Files), + Files = [test1, test2], + up_to_date = make:files(Files), % ok files + ok = ensure_exists(Files), - ?line error = make:files([test1,test7]), % non existing file - ?line up_to_date = make:files([test1,test2],[debug_info]), % with option + error = make:files([test1,test7]), % non existing file + up_to_date = make:files([test1,test2],[debug_info]), % with option - ?line file:set_cwd(Current), - ?line ensure_no_messages(), + file:set_cwd(Current), + ensure_no_messages(), ok. %% Moves to the data directory of this suite, clean it from any object %% files (*.jam for a JAM emulator). Returns the previous directory. prepare_data_dir(Config) -> - ?line {ok, Current} = file:get_cwd(), - ?line {value, {data_dir, Dir}} = lists:keysearch(data_dir, 1, Config), - ?line file:set_cwd(Dir), - ?line {ok, Files} = file:list_dir("."), - ?line delete_obj(Files, code:objfile_extension()), - ?line ensure_no_messages(), + {ok, Current} = file:get_cwd(), + {value, {data_dir, Dir}} = lists:keysearch(data_dir, 1, Config), + file:set_cwd(Dir), + {ok, Files} = file:list_dir("."), + delete_obj(Files, code:objfile_extension()), + ensure_no_messages(), Current. delete_obj([File|Rest], ObjExt) -> - ?line case filename:extension(File) of - ObjExt -> file:delete(File); - ".S" -> file:delete(File); - _ -> ok - end, - ?line delete_obj(Rest, ObjExt); + case filename:extension(File) of + ObjExt -> file:delete(File); + ".S" -> file:delete(File); + _ -> ok + end, + delete_obj(Rest, ObjExt); delete_obj([], _) -> ok. @@ -120,26 +118,26 @@ ensure_exists([Name|Rest], ObjExt) when is_atom(Name) -> ensure_exists([atom_to_list(Name)|Rest], ObjExt); ensure_exists([Name|Rest], ObjExt) -> case filelib:is_regular(Name++ObjExt) of - true -> - ensure_exists(Rest, ObjExt); - false -> - Name++ObjExt + true -> + ensure_exists(Rest, ObjExt); + false -> + Name++ObjExt end; ensure_exists([], _) -> ok. otp_6057_init(Config) when is_list(Config) -> - ?line DataDir = ?config(data_dir, Config), - ?line PrivDir = ?config(priv_dir, Config), + DataDir = proplists:get_value(data_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), %% Create the directories PrivDir/otp_6057/src1, /src2 and /ebin Src1 = filename:join([PrivDir, otp_6057, src1]), Src2 = filename:join([PrivDir, otp_6057, src2]), Ebin = filename:join([PrivDir, otp_6057, ebin]), - ?line ok = file:make_dir(filename:join(PrivDir, otp_6057)), - ?line ok = file:make_dir(Src1), - ?line ok = file:make_dir(Src2), - ?line ok = file:make_dir(Ebin), + ok = file:make_dir(filename:join(PrivDir, otp_6057)), + ok = file:make_dir(Src1), + ok = file:make_dir(Src2), + ok = file:make_dir(Ebin), %% Copy test1.erl and test2.erl to src1, and test3.erl to src2 Test1orig = filename:join(DataDir, "test1.erl"), @@ -148,35 +146,32 @@ otp_6057_init(Config) when is_list(Config) -> Test1 = filename:join(Src1, "test1.erl"), Test2 = filename:join(Src1, "test2.erl"), Test3 = filename:join(Src2, "test3.erl"), - ?line {ok, _} = file:copy(Test1orig, Test1), - ?line {ok, _} = file:copy(Test2orig, Test2), - ?line {ok, _} = file:copy(Test3orig, Test3), + {ok, _} = file:copy(Test1orig, Test1), + {ok, _} = file:copy(Test2orig, Test2), + {ok, _} = file:copy(Test3orig, Test3), %% Create an Emakefile in src1 Emakefile = filename:join(Src1, "Emakefile"), - ?line {ok, Fd} = file:open(Emakefile, write), - ?line ok = io:write(Fd, {["test1.erl","test2","../src2/test3"], - [{outdir,"../ebin"}]}), - ?line ok = io:fwrite(Fd, ".~n", []), - ?line ok = file:close(Fd), + {ok, Fd} = file:open(Emakefile, write), + ok = io:write(Fd, {["test1.erl","test2","../src2/test3"], + [{outdir,"../ebin"}]}), + ok = io:fwrite(Fd, ".~n", []), + ok = file:close(Fd), - ?line ensure_no_messages(), + ensure_no_messages(), Config. -otp_6057_a(suite) -> - []; -otp_6057_a(doc) -> - ["Test that make:all/0, suite/0 looks for object file in correct place"]; +%% Test that make:all/0, suite/0 looks for object file in correct place otp_6057_a(Config) when is_list(Config) -> - ?line PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), %% Go to src1, saving old CWD - ?line {ok, CWD} = file:get_cwd(), + {ok, CWD} = file:get_cwd(), Src1 = filename:join([PrivDir, otp_6057, src1]), - ?line ok = file:set_cwd(Src1), + ok = file:set_cwd(Src1), %% Call make:all() - ?line up_to_date = make:all(), + up_to_date = make:all(), %% Ensure that all beam files are created in the ebin directory Ebin = filename:join([PrivDir, otp_6057, ebin]), @@ -184,109 +179,103 @@ otp_6057_a(Config) when is_list(Config) -> Test2 = filename:join(Ebin, test2), Test3 = filename:join(Ebin, test3), case ensure_exists([Test1, Test2, Test3]) of - ok -> ok; - Missing -> - ?line ?t:fail({"missing beam file", Missing}) + ok -> ok; + Missing -> + ct:fail({"missing beam file", Missing}) end, %% Check creation date of test1.beam and make sure it is not %% recompiled if make:all() is called again. %% (Sleep a while, if the file is recompiled within a second then %% mtime will be the same). - ?line {ok, FileInfo1} = file:read_file_info(Test1++".beam"), + {ok, FileInfo1} = file:read_file_info(Test1++".beam"), Date1 = FileInfo1#file_info.mtime, - ?t:sleep(?t:seconds(2)), - ?line up_to_date = make:all(), - ?line {ok, FileInfo2} = file:read_file_info(Test1++".beam"), + timer:sleep(2000), + up_to_date = make:all(), + {ok, FileInfo2} = file:read_file_info(Test1++".beam"), case FileInfo2#file_info.mtime of - Date1 -> ok; - _Date2 -> - ?line ?t:fail({"recompiled beam file", Test1++".beam"}) + Date1 -> ok; + _Date2 -> + ct:fail({"recompiled beam file", Test1++".beam"}) end, %% Remove the beam files - ?line ok = - ensure_removed([Test1++".beam",Test2++".beam",Test2++".beam"]), + ok = + ensure_removed([Test1++".beam",Test2++".beam",Test2++".beam"]), %% Return to original CWD - ?line ok = file:set_cwd(CWD), + ok = file:set_cwd(CWD), - ?line ensure_no_messages(), + ensure_no_messages(), ok. -otp_6057_b(suite) -> - []; -otp_6057_b(doc) -> - ["Test that make:files/1 can handle a file in another directory"]; +%% Test that make:files/1 can handle a file in another directory otp_6057_b(Config) when is_list(Config) -> - ?line PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), %% Go to src1, saving old CWD - ?line {ok, CWD} = file:get_cwd(), + {ok, CWD} = file:get_cwd(), Src1 = filename:join([PrivDir, otp_6057, src1]), - ?line ok = file:set_cwd(Src1), + ok = file:set_cwd(Src1), %% Ensure there is no beam file already Ebin = filename:join([PrivDir, otp_6057, ebin]), Test3 = filename:join(Ebin, "test3"), - ?line ok = ensure_removed([Test3++".beam"]), + ok = ensure_removed([Test3++".beam"]), %% Call make:files/1 - ?line up_to_date = make:files(["../src2/test3"]), - + up_to_date = make:files(["../src2/test3"]), + %% Ensure that the beam file is created in the ebin directory case ensure_exists([Test3]) of - ok -> ok; - Missing -> - ?line ?t:fail({"missing beam file", Missing}) + ok -> ok; + Missing -> + ct:fail({"missing beam file", Missing}) end, %% Remove the beam file - ?line ok = ensure_removed([Test3++".beam"]), + ok = ensure_removed([Test3++".beam"]), %% Return to original CWD - ?line ok = file:set_cwd(CWD), + ok = file:set_cwd(CWD), - ?line ensure_no_messages(), + ensure_no_messages(), ok. -otp_6057_c(suite) -> - []; -otp_6057_c(doc) -> - ["Test that make:files/1 find options in Emakefile if a file is " - "given with the .erl extension there"]; +%% Test that make:files/1 find options in Emakefile if a file is +%% given with the .erl extension there otp_6057_c(Config) when is_list(Config) -> - ?line PrivDir = ?config(priv_dir, Config), + PrivDir = proplists:get_value(priv_dir, Config), %% Go to src1, saving old CWD - ?line {ok, CWD} = file:get_cwd(), + {ok, CWD} = file:get_cwd(), Src1 = filename:join([PrivDir, otp_6057, src1]), - ?line ok = file:set_cwd(Src1), + ok = file:set_cwd(Src1), %% Ensure there are no beam files already Ebin = filename:join([PrivDir, otp_6057, ebin]), Test1 = filename:join(Ebin, "test1"), Test2 = filename:join(Ebin, "test2"), - ?line ok = ensure_removed([Test1++".beam",Test2++".beam"]), + ok = ensure_removed([Test1++".beam",Test2++".beam"]), %% Call make:files/1 - ?line up_to_date = make:files([test1, test2]), - + up_to_date = make:files([test1, test2]), + %% Ensure that the beam files are created in the ebin directory Ebin = filename:join([PrivDir, otp_6057, ebin]), case ensure_exists([Test1, Test2]) of - ok -> ok; - Missing -> - ?line ?t:fail({"missing beam file", Missing}) + ok -> ok; + Missing -> + ct:fail({"missing beam file", Missing}) end, %% Remove the beam files - ?line ok = ensure_removed([Test1++".beam", Test2++".beam"]), + ok = ensure_removed([Test1++".beam", Test2++".beam"]), %% Return to original CWD - ?line ok = file:set_cwd(CWD), + ok = file:set_cwd(CWD), - ?line ensure_no_messages(), + ensure_no_messages(), ok. otp_6057_end(Config) when is_list(Config) -> @@ -303,13 +292,12 @@ ensure_no_messages() -> ensure_no_messages(N) -> receive - Any -> - io:format("Unexpected message: ~p", [Any]), - ensure_no_messages(N+1) + Any -> + io:format("Unexpected message: ~p", [Any]), + ensure_no_messages(N+1) after 0 -> - case N of - 0 -> ok; - N -> ?t:fail() - end + case N of + 0 -> ok; + N -> ct:fail(failed) + end end. - diff --git a/lib/tools/test/tools_SUITE.erl b/lib/tools/test/tools_SUITE.erl index ae2a69305b..b50f67a06a 100644 --- a/lib/tools/test/tools_SUITE.erl +++ b/lib/tools/test/tools_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1997-2011. All Rights Reserved. +%% Copyright Ericsson AB 1997-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -21,58 +21,29 @@ -include_lib("common_test/include/ct.hrl"). -%% Default timetrap timeout (set in init_per_testcase). --define(default_timeout, ?t:minutes(1)). -define(application, tools). %% Test server specific exports --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2]). --export([init_per_testcase/2, end_per_testcase/2]). +-export([all/0, suite/0]). %% Test cases must be exported. -export([app_test/1, appup_test/1]). -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{minutes,1}}]. all() -> [app_test, appup_test]. -groups() -> - []. - -init_per_suite(Config) -> - Config. - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - - -init_per_testcase(_Case, Config) -> - ?line Dog=test_server:timetrap(?default_timeout), - [{watchdog, Dog}|Config]. -end_per_testcase(_Case, Config) -> - Dog=?config(watchdog, Config), - test_server:timetrap_cancel(Dog), - ok. - %%% %%% Test cases starts here. %%% -app_test(doc) -> - ["Test that the .app file does not contain any `basic' errors"]; -app_test(suite) -> - []; +%% Test that the .app file does not contain any `basic' errors app_test(Config) when is_list(Config) -> - ?line ?t:app_test(tools, tolerant). + test_server:app_test(tools, tolerant). %% Test that the .appup file does not contain any `basic' errors appup_test(Config) when is_list(Config) -> - ok = ?t:appup_test(tools). + ok = test_server:appup_test(tools). diff --git a/lib/tools/test/xref_SUITE.erl b/lib/tools/test/xref_SUITE.erl index 53aa80d2a3..ce30fb711a 100644 --- a/lib/tools/test/xref_SUITE.erl +++ b/lib/tools/test/xref_SUITE.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2000-2013. All Rights Reserved. +%% Copyright Ericsson AB 2000-2016. All Rights Reserved. %% %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. @@ -32,46 +32,41 @@ -else. -include_lib("common_test/include/ct.hrl"). -define(format(S, A), ok). --define(datadir, ?config(data_dir, Conf)). --define(privdir, ?config(priv_dir, Conf)). --define(copydir, ?config(copy_dir, Conf)). +-define(datadir, proplists:get_value(data_dir, Conf)). +-define(privdir, proplists:get_value(priv_dir, Conf)). +-define(copydir, proplists:get_value(copy_dir, Conf)). -endif. --export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, - init_per_group/2,end_per_group/2, init/1, fini/1]). +-export([all/0, suite/0, groups/0, + init_per_suite/1, end_per_suite/1]). --export([ - addrem/1, convert/1, intergraph/1, lines/1, loops/1, - no_data/1, modules/1]). +-export([addrem/1, convert/1, intergraph/1, lines/1, loops/1, + no_data/1, modules/1]). --export([ - add/1, default/1, info/1, lib/1, read/1, read2/1, remove/1, - replace/1, update/1, deprecated/1, trycatch/1, +-export([add/1, default/1, info/1, lib/1, read/1, read2/1, remove/1, + replace/1, update/1, deprecated/1, trycatch/1, fun_mfa/1, fun_mfa_r14/1, - fun_mfa_vars/1, qlc/1]). + fun_mfa_vars/1, qlc/1]). --export([ - analyze/1, basic/1, md/1, q/1, variables/1, unused_locals/1]). +-export([analyze/1, basic/1, md/1, q/1, variables/1, unused_locals/1]). --export([ - format_error/1, otp_7423/1, otp_7831/1, otp_10192/1]). +-export([format_error/1, otp_7423/1, otp_7831/1, otp_10192/1]). -import(lists, [append/2, flatten/1, keysearch/3, member/2, sort/1, usort/1]). -import(sofs, [converse/1, from_term/1, intersection/2, is_sofs_set/1, - range/1, relation_to_family/1, set/1, to_external/1, - union/2]). - --export([init_per_testcase/2, end_per_testcase/2]). + range/1, relation_to_family/1, set/1, to_external/1, + union/2]). %% Checks some info counters of a server and some relations that should hold. -export([check_count/1, check_state/1]). -include_lib("kernel/include/file.hrl"). - -include_lib("tools/src/xref.hrl"). -suite() -> [{ct_hooks,[ts_install_cth]}]. +suite() -> + [{ct_hooks,[ts_install_cth]}, + {timetrap,{minutes,2}}]. all() -> [{group, xref}, {group, files}, {group, analyses}, @@ -89,48 +84,24 @@ groups() -> [analyze, basic, md, q, variables, unused_locals]}, {misc, [], [format_error, otp_7423, otp_7831, otp_10192]}]. -init_per_suite(Config) -> - init(Config). - -end_per_suite(_Config) -> - ok. - -init_per_group(_GroupName, Config) -> - Config. - -end_per_group(_GroupName, Config) -> - Config. - -init(Conf) when is_list(Conf) -> +init_per_suite(Conf) when is_list(Conf) -> DataDir = ?datadir, PrivDir = ?privdir, - ?line CopyDir = fname(PrivDir, "datacopy"), - ?line TarFile = fname(PrivDir, "datacopy.tgz"), - ?line {ok, Tar} = erl_tar:open(TarFile, [write, compressed]), - ?line ok = erl_tar:add(Tar, DataDir, CopyDir, [compressed]), - ?line ok = erl_tar:close(Tar), - ?line ok = erl_tar:extract(TarFile, [compressed]), - ?line ok = file:delete(TarFile), - [{copy_dir, CopyDir} | Conf]. - -fini(Conf) when is_list(Conf) -> - %% Nothing. - Conf. - -init_per_testcase(_Case, Config) -> - Dog=?t:timetrap(?t:minutes(2)), - [{watchdog, Dog}|Config]. - -end_per_testcase(_Case, _Config) -> - Dog=?config(watchdog, _Config), - test_server:timetrap_cancel(Dog), + CopyDir = fname(PrivDir, "datacopy"), + TarFile = fname(PrivDir, "datacopy.tgz"), + {ok, Tar} = erl_tar:open(TarFile, [write, compressed]), + ok = erl_tar:add(Tar, DataDir, CopyDir, [compressed]), + ok = erl_tar:close(Tar), + ok = erl_tar:extract(TarFile, [compressed]), + ok = file:delete(TarFile), + [{copy_dir, CopyDir}|Conf]. + +end_per_suite(Conf) when is_list(Conf) -> ok. - %% Seems a bit short... -addrem(suite) -> []; -addrem(doc) -> ["Simple test of removing modules"]; +%% Simple test of removing modules addrem(Conf) when is_list(Conf) -> S0 = new(), @@ -149,8 +120,8 @@ addrem(Conf) when is_list(Conf) -> LCallAt_m1 = [], XCallAt_m1 = [{E1,13}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), D2 = {F2,7}, DefAt_m2 = [D2], @@ -161,26 +132,25 @@ addrem(Conf) when is_list(Conf) -> LCallAt_m2 = [], XCallAt_m2 = [{E2,96}], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), - - ?line S5 = set_up(S2), - - ?line {ok, XMod1, S6} = remove_module(S5, m1), - ?line [a1] = XMod1#xref_mod.app_name, - ?line {ok, XMod2, S6a} = remove_module(S6, m2), - ?line [a2] = XMod2#xref_mod.app_name, - ?line S7 = set_up(S6a), - - ?line AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, - ?line S9 = add_application(S7, AppInfo1), - ?line S10 = set_up(S9), - ?line AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, - ?line _S11 = add_application(S10, AppInfo2), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), + + S5 = set_up(S2), + + {ok, XMod1, S6} = remove_module(S5, m1), + [a1] = XMod1#xref_mod.app_name, + {ok, XMod2, S6a} = remove_module(S6, m2), + [a2] = XMod2#xref_mod.app_name, + S7 = set_up(S6a), + + AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, + S9 = add_application(S7, AppInfo1), + S10 = set_up(S9), + AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, + _S11 = add_application(S10, AppInfo2), ok. -convert(suite) -> []; -convert(doc) -> ["Coercion of data"]; +%% Coercion of data convert(Conf) when is_list(Conf) -> S0 = new(), @@ -215,8 +185,8 @@ convert(Conf) when is_list(Conf) -> LCallAt_m1 = [], XCallAt_m1 = [{E1,13},{E2,17},{E4,7}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), D2 = {F2,7}, D3 = {F3,9}, @@ -229,8 +199,8 @@ convert(Conf) when is_list(Conf) -> LCallAt_m2 = [], XCallAt_m2 = [{E3,96},{E6,12},{UE1,77}], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), D4 = {F4,6}, D5 = {F5,97}, @@ -242,74 +212,74 @@ convert(Conf) when is_list(Conf) -> LCallAt_m3 = [{E5,19}], XCallAt_m3 = [{UE2,22}], Info3 = #xref_mod{name = m3, app_name = [a3]}, - ?line S3 = add_module(S2, Info3, DefAt_m3, X_m3, LCallAt_m3, XCallAt_m3, - XC_m3, LC_m3), + S3 = add_module(S2, Info3, DefAt_m3, X_m3, LCallAt_m3, XCallAt_m3, + XC_m3, LC_m3), Info4 = #xref_mod{name = m4, app_name = [a2]}, - ?line S4 = add_module(S3, Info4, [], [], [], [], [], []), + S4 = add_module(S3, Info4, [], [], [], [], [], []), AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, - ?line S9 = add_application(S4, AppInfo1), + S9 = add_application(S4, AppInfo1), AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, - ?line S10 = add_application(S9, AppInfo2), + S10 = add_application(S9, AppInfo2), AppInfo3 = #xref_app{name = a3, rel_name = [r2]}, - ?line S11 = add_application(S10, AppInfo3), + S11 = add_application(S10, AppInfo3), RelInfo1 = #xref_rel{name = r1}, - ?line S12 = add_release(S11, RelInfo1), + S12 = add_release(S11, RelInfo1), RelInfo2 = #xref_rel{name = r2}, - ?line S13 = add_release(S12, RelInfo2), + S13 = add_release(S12, RelInfo2), - ?line S = set_up(S13), + S = set_up(S13), - ?line {ok, _} = eval("(Lin)(m1->m1:Mod) * m1->m1", type_error, S), - ?line {ok, _} = eval("(XXL)(Lin)(m1->m1:Mod) * m1->m1", type_error, S), + {ok, _} = eval("(Lin)(m1->m1:Mod) * m1->m1", type_error, S), + {ok, _} = eval("(XXL)(Lin)(m1->m1:Mod) * m1->m1", type_error, S), - ?line AllDefAt = eval("(Lin) M", S), - ?line AllV = eval("(Fun) M", S), - ?line AllCallAt = eval("(XXL)(Lin) E", S), - ?line AllE = eval("E", S), + AllDefAt = eval("(Lin) M", S), + AllV = eval("(Fun) M", S), + AllCallAt = eval("(XXL)(Lin) E", S), + AllE = eval("E", S), - ?line AM = eval("AM", S), - ?line A = eval("A", S), - ?line R = eval("R", S), + AM = eval("AM", S), + A = eval("A", S), + R = eval("R", S), % vertices % general 1 step - ?line {ok, _} = eval("(Fun) (Lin) M", AllV, S), - ?line {ok, _} = eval("(Fun) (Lin) (Lin) M", AllV, S), - ?line {ok, _} = eval(f("(Fun) (Lin) ~p", [[F1, F3]]), [F1,F3], S), - ?line {ok, _} = eval(f("(Mod) ~p", [AllV]), [m1,m17,m2,m3], S), - ?line {ok, _} = eval(f("(Mod) ~p", [[F1,F3,F6]]), [m1,m2], S), - ?line {ok, _} = eval("(App) M", A, S), - ?line {ok, _} = eval(f("(App) ~p", [[m1,m2,m4]]), [a1,a2], S), - ?line {ok, _} = eval(f("(Rel) ~p", [A]), R, S), - ?line {ok, _} = eval(f("(Rel) ~p", [[a1,a2,a2]]), [r1], S), + {ok, _} = eval("(Fun) (Lin) M", AllV, S), + {ok, _} = eval("(Fun) (Lin) (Lin) M", AllV, S), + {ok, _} = eval(f("(Fun) (Lin) ~p", [[F1, F3]]), [F1,F3], S), + {ok, _} = eval(f("(Mod) ~p", [AllV]), [m1,m17,m2,m3], S), + {ok, _} = eval(f("(Mod) ~p", [[F1,F3,F6]]), [m1,m2], S), + {ok, _} = eval("(App) M", A, S), + {ok, _} = eval(f("(App) ~p", [[m1,m2,m4]]), [a1,a2], S), + {ok, _} = eval(f("(Rel) ~p", [A]), R, S), + {ok, _} = eval(f("(Rel) ~p", [[a1,a2,a2]]), [r1], S), % general 2 steps - ?line {ok, _} = eval("(Mod) (Lin) M", [m1,m17,m2,m3], S), - ?line {ok, _} = eval(f("(App) ~p", [AllV]), [a1,a2,a3], S), - ?line {ok, _} = eval("(Rel) M", R, S), + {ok, _} = eval("(Mod) (Lin) M", [m1,m17,m2,m3], S), + {ok, _} = eval(f("(App) ~p", [AllV]), [a1,a2,a3], S), + {ok, _} = eval("(Rel) M", R, S), % general 4 steps - ?line {ok, _} = eval("(Rel) (Lin) M", [r1,r2], S), + {ok, _} = eval("(Rel) (Lin) M", [r1,r2], S), % special 1 step - ?line {ok, _} = eval(f("(Lin) ~p", [AllV]), AllDefAt, S), - ?line {ok, _} = eval(f("(Lin) ~p", [[F1,F3]]), [{F1,12},{F3,9}], S), - ?line {ok, _} = eval("(Fun) M", AllV, S), - ?line {ok, _} = eval(f("(Fun) ~p", [[m1,m2]]), [F1,F2,F3,F6,F7,UF1], S), - ?line {ok, _} = eval(f("(Mod) ~p", [A]), AM, S), - ?line {ok, _} = eval(f("(Mod) ~p", [[a1,a2]]), [m1,m2,m4], S), - ?line {ok, _} = eval(f("(App) ~p", [R]), A, S), - ?line {ok, _} = eval(f("(App) ~p", [[r1]]), [a1,a2], S), + {ok, _} = eval(f("(Lin) ~p", [AllV]), AllDefAt, S), + {ok, _} = eval(f("(Lin) ~p", [[F1,F3]]), [{F1,12},{F3,9}], S), + {ok, _} = eval("(Fun) M", AllV, S), + {ok, _} = eval(f("(Fun) ~p", [[m1,m2]]), [F1,F2,F3,F6,F7,UF1], S), + {ok, _} = eval(f("(Mod) ~p", [A]), AM, S), + {ok, _} = eval(f("(Mod) ~p", [[a1,a2]]), [m1,m2,m4], S), + {ok, _} = eval(f("(App) ~p", [R]), A, S), + {ok, _} = eval(f("(App) ~p", [[r1]]), [a1,a2], S), % special 2 steps - ?line {ok, _} = eval("(Lin) M", AllDefAt, S), - ?line AnalyzedV = eval("(Fun) AM", S), - ?line {ok, _} = eval(f("(Fun) ~p", [A]), AnalyzedV, S), - ?line {ok, _} = eval(f("(Mod) ~p", [R]), AM, S), + {ok, _} = eval("(Lin) M", AllDefAt, S), + AnalyzedV = eval("(Fun) AM", S), + {ok, _} = eval(f("(Fun) ~p", [A]), AnalyzedV, S), + {ok, _} = eval(f("(Mod) ~p", [R]), AM, S), % special 4 steps - ?line AnalyzedAllDefAt = eval("(Lin) AM", S), - ?line {ok, _} = eval("(Lin) R", AnalyzedAllDefAt, S), + AnalyzedAllDefAt = eval("(Lin) AM", S), + {ok, _} = eval("(Lin) R", AnalyzedAllDefAt, S), % edges Ms = [{m1,m2},{m1,m3},{m2,m1},{m2,m3},{m3,m3}], @@ -319,31 +289,30 @@ convert(Conf) when is_list(Conf) -> Rs = [{r1,r1},{r1,r2},{r2,r2}], % general 1 step - ?line {ok, _} = eval("(Fun) (Lin) E", AllE, S), - ?line {ok, _} = eval(f("(Fun)(Lin) ~p", [[E1, E6]]), [E1, E6], S), - ?line {ok, _} = eval("(Mod) E", AllMs, S), - ?line {ok, _} = eval(f("(Mod) ~p", [[E1, E6]]), [{m1,m2},{m2,m3}], S), - ?line {ok, _} = eval(f("(App) ~p", [As]), As, S), - ?line {ok, _} = eval("(App) [m1->m2,m2->m3]", [{a1,a2},{a2,a3}], S), - ?line {ok, _} = eval(f("(Rel) ~p", [As]), Rs, S), - ?line {ok, _} = eval("(Rel) a1->a2", [{r1,r1}], S), + {ok, _} = eval("(Fun) (Lin) E", AllE, S), + {ok, _} = eval(f("(Fun)(Lin) ~p", [[E1, E6]]), [E1, E6], S), + {ok, _} = eval("(Mod) E", AllMs, S), + {ok, _} = eval(f("(Mod) ~p", [[E1, E6]]), [{m1,m2},{m2,m3}], S), + {ok, _} = eval(f("(App) ~p", [As]), As, S), + {ok, _} = eval("(App) [m1->m2,m2->m3]", [{a1,a2},{a2,a3}], S), + {ok, _} = eval(f("(Rel) ~p", [As]), Rs, S), + {ok, _} = eval("(Rel) a1->a2", [{r1,r1}], S), % special 1 step - ?line {ok, _} = eval("(XXL) (Lin) (Fun) E", AllCallAt, S), - ?line {ok, _} = eval("(XXL) (XXL) (Lin) (Fun) E", AllCallAt, S), - - ?line {ok, _} = eval(f("(XXL) (Lin) ~p", [[E1, E6]]), - [{{D1,D3},[13]}, {{D7,D4},[12]}], S), - ?line {ok, _} = eval(f("(Fun) ~p", [AllMs]), AllE, S), - ?line {ok, _} = eval("(Fun) [m1->m2,m2->m3]", [E1,E2,E6], S), - ?line {ok, _} = eval(f("(Mod) ~p", [As]), Ms, S), - ?line {ok, _} = eval("(Mod) [a1->a2,a2->a3]", [{m1,m2},{m2,m3}], S), - ?line {ok, _} = eval(f("(App) ~p", [Rs]), As, S), - ?line {ok, _} = eval("(App) r1->r1", [{a1,a2},{a2,a1}], S), + {ok, _} = eval("(XXL) (Lin) (Fun) E", AllCallAt, S), + {ok, _} = eval("(XXL) (XXL) (Lin) (Fun) E", AllCallAt, S), + + {ok, _} = eval(f("(XXL) (Lin) ~p", [[E1, E6]]), + [{{D1,D3},[13]}, {{D7,D4},[12]}], S), + {ok, _} = eval(f("(Fun) ~p", [AllMs]), AllE, S), + {ok, _} = eval("(Fun) [m1->m2,m2->m3]", [E1,E2,E6], S), + {ok, _} = eval(f("(Mod) ~p", [As]), Ms, S), + {ok, _} = eval("(Mod) [a1->a2,a2->a3]", [{m1,m2},{m2,m3}], S), + {ok, _} = eval(f("(App) ~p", [Rs]), As, S), + {ok, _} = eval("(App) r1->r1", [{a1,a2},{a2,a1}], S), ok. -intergraph(suite) -> []; -intergraph(doc) -> ["Inter Call Graph"]; +%% Inter Call Graph intergraph(Conf) when is_list(Conf) -> S0 = new(), @@ -392,8 +361,8 @@ intergraph(Conf) when is_list(Conf) -> LCallAt_m1 = [{E1,1},{E2,2},{E3,3},{E5,5},{E6,6},{E7,7}], XCallAt_m1 = [{E1,4}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), D6 = {F6,6}, D7 = {F7,7}, @@ -409,73 +378,72 @@ intergraph(Conf) when is_list(Conf) -> LCallAt_m2 = [{E8,8},{E9,9},{E11,11},{E12,12},{E13,13},{E14,14}], XCallAt_m2 = [{E10,10},{E15,15}], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, - ?line S5 = add_application(S2, AppInfo1), + S5 = add_application(S2, AppInfo1), AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, - ?line S6 = add_application(S5, AppInfo2), + S6 = add_application(S5, AppInfo2), RelInfo = #xref_rel{name = r1}, - ?line S7 = add_release(S6, RelInfo), + S7 = add_release(S6, RelInfo), - ?line S = set_up(S7), + S = set_up(S7), - ?line {ok, _} = eval("EE | m1", [E1,E5,E6,E7], S), - ?line {ok, _} = eval("EE | m2", [{F6,F1}], S), - ?line {ok, _} = eval("EE | m2 + EE | m2", [{F6,F1}], S), + {ok, _} = eval("EE | m1", [E1,E5,E6,E7], S), + {ok, _} = eval("EE | m2", [{F6,F1}], S), + {ok, _} = eval("EE | m2 + EE | m2", [{F6,F1}], S), - ?line {ok, _} = eval("(Fun)(Lin)(E | m1)", - to_external(union(set(XC_m1), set(LC_m1))), S), - ?line {ok, _} = eval("(XXL)(ELin) (EE | m1)", - [{{D2,D1},[1,2,4]},{{D4,D2},[5]},{{D5,D4},[6]},{{D4,D5},[7]}], - S), - ?line {ok, _} = eval("(XXL)(ELin)(EE | m2)", [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(ELin)(EE | m2)", - [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(Fun)(Lin)(E | m1)", + to_external(union(set(XC_m1), set(LC_m1))), S), + {ok, _} = eval("(XXL)(ELin) (EE | m1)", + [{{D2,D1},[1,2,4]},{{D4,D2},[5]},{{D5,D4},[6]},{{D4,D5},[7]}], + S), + {ok, _} = eval("(XXL)(ELin)(EE | m2)", [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(XXL)(ELin)(ELin)(EE | m2)", + [{{D6,D1},[8,11,12]}], S), %% Combining graphs (equal or different): - ?line {ok, _} = eval("(XXL)(ELin)(EE | m2 + EE | m2)", - [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(EE | m2 * EE | m2)", - [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(EE | m2 - EE | m1)", - [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(EE | m2 - E | m2)", - [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(Fun)(ELin)(EE | m2)", - [{{D6,D1},[8,11,12]}], S), - ?line {ok, _} = eval("EE | m1 + E | m1", LC_m1, S), - ?line {ok, _} = eval(f("EE | ~p + E | ~p", [F2, F2]), [E1,E2], S), + {ok, _} = eval("(XXL)(ELin)(EE | m2 + EE | m2)", + [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(XXL)(ELin)(EE | m2 * EE | m2)", + [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(XXL)(ELin)(EE | m2 - EE | m1)", + [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(XXL)(ELin)(EE | m2 - E | m2)", + [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("(XXL)(ELin)(Fun)(ELin)(EE | m2)", + [{{D6,D1},[8,11,12]}], S), + {ok, _} = eval("EE | m1 + E | m1", LC_m1, S), + {ok, _} = eval(f("EE | ~p + E | ~p", [F2, F2]), [E1,E2], S), %% [1,4] from 'calls' is a subset of [1,2,4] from Inter Call Graph: - ?line {ok, _} = eval(f("(XXL)(Lin) (E | ~p)", [F2]), - [{{D2,D1},[1,4]},{{D2,D3},[2]}], S), - - ?line {ok, _} = eval(f("(XXL)(ELin) (EE | ~p)", [F2]), - [{{D2,D1},[1,2,4]}], S), - ?line {ok, _} = eval(f("(XXL)((ELin)(EE | ~p) + (Lin)(E | ~p))", [F2, F2]), - [{{D2,D1},[1,2,4]},{{D2,D3},[2]}], S), - ?line {ok, _} = - eval(f("(XXL)((ELin) ~p + (Lin) ~p)", [{F2, F1}, {F2, F1}]), - [{{D2,D1},[1,2,4]}], S), - ?line {ok, _} = eval(f("(Fun)(Lin) ~p", [{F2, F1}]), [E1], S), + {ok, _} = eval(f("(XXL)(Lin) (E | ~p)", [F2]), + [{{D2,D1},[1,4]},{{D2,D3},[2]}], S), + + {ok, _} = eval(f("(XXL)(ELin) (EE | ~p)", [F2]), + [{{D2,D1},[1,2,4]}], S), + {ok, _} = eval(f("(XXL)((ELin)(EE | ~p) + (Lin)(E | ~p))", [F2, F2]), + [{{D2,D1},[1,2,4]},{{D2,D3},[2]}], S), + {ok, _} = + eval(f("(XXL)((ELin) ~p + (Lin) ~p)", [{F2, F1}, {F2, F1}]), + [{{D2,D1},[1,2,4]}], S), + {ok, _} = eval(f("(Fun)(Lin) ~p", [{F2, F1}]), [E1], S), %% The external call E4 is included in the reply: - ?line {ok, _} = eval("(XXL)(Lin)(LC | m1)", - [{{D2,D1},[1,4]},{{D2,D3},[2]},{{D3,D1},[3]}, - {{D4,D2},[5]},{{D4,D5},[7]},{{D5,D4},[6]}], S), + {ok, _} = eval("(XXL)(Lin)(LC | m1)", + [{{D2,D1},[1,4]},{{D2,D3},[2]},{{D3,D1},[3]}, + {{D4,D2},[5]},{{D4,D5},[7]},{{D5,D4},[6]}], S), %% The local call E1 is included in the reply: - ?line {ok, _} = eval("(XXL)(Lin)(XC | m1)", [{{D2,D1},[1,4]}], S), + {ok, _} = eval("(XXL)(Lin)(XC | m1)", [{{D2,D1},[1,4]}], S), - ?line {ok, _} = eval(f("(LLin) (E | ~p || ~p) + (XLin) (E | ~p || ~p)", - [F2, F1, F2, F1]), [{E4,[1,4]}], S), + {ok, _} = eval(f("(LLin) (E | ~p || ~p) + (XLin) (E | ~p || ~p)", + [F2, F1, F2, F1]), [{E4,[1,4]}], S), - ?line {ok, _} = eval("# (ELin) E", 6, S), + {ok, _} = eval("# (ELin) E", 6, S), ok. -lines(suite) -> []; -lines(doc) -> ["More test of Inter Call Graph, and regular expressions"]; +%% More test of Inter Call Graph, and regular expressions lines(Conf) when is_list(Conf) -> S0 = new(), @@ -509,8 +477,8 @@ lines(Conf) when is_list(Conf) -> LCallAt_m1 = [{E1,1},{E3,3},{E6,6}], XCallAt_m1 = [{E2,2},{E4,4},{E5,5},{E7,7}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), DefAt_m2 = [D4], X_m2 = [F4], @@ -520,81 +488,80 @@ lines(Conf) when is_list(Conf) -> LCallAt_m2 = [], XCallAt_m2 = [], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, - ?line S5 = add_application(S2, AppInfo1), + S5 = add_application(S2, AppInfo1), AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, - ?line S6 = add_application(S5, AppInfo2), + S6 = add_application(S5, AppInfo2), RelInfo = #xref_rel{name = r1}, - ?line S7 = add_release(S6, RelInfo), - - ?line S = set_up(S7), - - ?line {ok, _} = eval("(XXL) (ELin) (EE | m1)", - [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, - {{D5,D4},[6]}], S), - ?line {ok, _} = eval("(XXL)(Lin) (E | m1)", - [{{D1,D2},[1]},{{D1,D4},[4]},{{D2,D1},[2]}, - {{D2,D4},[5]},{{D3,D2},[3]},{{D5,D6},[6]},{{D6,D4},[7]}], - S), - ?line {ok, _} = eval("(E | m1) + (EE | m1)", - [E1,E2,E3,E4,E5,E6,E7,{F1,F1},{F3,F1},{F3,F4},{F5,F4}], - S), - ?line {ok, _} = eval("(Lin)(E | m1)", - [{E4,[4]},{E1,[1]},{E2,[2]},{E5,[5]}, - {E3,[3]},{E7,[7]},{E6,[6]}], S), - ?line {ok, _} = eval("(ELin)(EE | m1)", - [{{F1,F1},[1]},{{F1,F4},[1,4]},{{F3,F1},[3]},{{F3,F4},[3]}, - {{F5,F4},[6]}], S), - ?line {ok, _} = eval("(Lin)(E | m1) + (ELin)(EE | m1)", - [{E4,[1,4]},{E1,[1]},{E2,[2]},{E5,[5]}, - {E3,[3]},{E7,[7]},{E6,[6]}, - {{F1,F1},[1]},{{F3,F1},[3]},{{F3,F4},[3]}, - {{F5,F4},[6]}], S), - ?line {ok, _} = eval("(Lin)(E | m1) - (ELin)(EE | m1)", - [{E1,[1]},{E2,[2]},{E5,[5]}, - {E3,[3]},{E7,[7]},{E6,[6]}], S), - ?line {ok, _} = eval("(Lin)(E | m1) * (ELin)(EE | m1)", - [{E4,[4]}], S), - ?line {ok, _} = eval("(XXL)(Lin) (E | m1)", - [{{D1,D4},[4]},{{D1,D2},[1]},{{D2,D1},[2]},{{D2,D4},[5]}, - {{D3,D2},[3]},{{D6,D4},[7]},{{D5,D6},[6]}], S), - ?line {ok, _} = eval("(XXL)(ELin) (EE | m1)", - [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, - {{D5,D4},[6]}], S), - ?line {ok, _} = eval("(XXL)(Lin)(Fun)(Lin) (E | m1)", - [{{D1,D4},[4]},{{D1,D2},[1]},{{D2,D1},[2]},{{D2,D4},[5]}, - {{D3,D2},[3]},{{D6,D4},[7]},{{D5,D6},[6]}], S), - ?line {ok, _} = eval("(XXL)(ELin)(Fun)(ELin) (EE | m1)", - [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, - {{D5,D4},[6]}], S), + S7 = add_release(S6, RelInfo), + + S = set_up(S7), + + {ok, _} = eval("(XXL) (ELin) (EE | m1)", + [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, + {{D5,D4},[6]}], S), + {ok, _} = eval("(XXL)(Lin) (E | m1)", + [{{D1,D2},[1]},{{D1,D4},[4]},{{D2,D1},[2]}, + {{D2,D4},[5]},{{D3,D2},[3]},{{D5,D6},[6]},{{D6,D4},[7]}], + S), + {ok, _} = eval("(E | m1) + (EE | m1)", + [E1,E2,E3,E4,E5,E6,E7,{F1,F1},{F3,F1},{F3,F4},{F5,F4}], + S), + {ok, _} = eval("(Lin)(E | m1)", + [{E4,[4]},{E1,[1]},{E2,[2]},{E5,[5]}, + {E3,[3]},{E7,[7]},{E6,[6]}], S), + {ok, _} = eval("(ELin)(EE | m1)", + [{{F1,F1},[1]},{{F1,F4},[1,4]},{{F3,F1},[3]},{{F3,F4},[3]}, + {{F5,F4},[6]}], S), + {ok, _} = eval("(Lin)(E | m1) + (ELin)(EE | m1)", + [{E4,[1,4]},{E1,[1]},{E2,[2]},{E5,[5]}, + {E3,[3]},{E7,[7]},{E6,[6]}, + {{F1,F1},[1]},{{F3,F1},[3]},{{F3,F4},[3]}, + {{F5,F4},[6]}], S), + {ok, _} = eval("(Lin)(E | m1) - (ELin)(EE | m1)", + [{E1,[1]},{E2,[2]},{E5,[5]}, + {E3,[3]},{E7,[7]},{E6,[6]}], S), + {ok, _} = eval("(Lin)(E | m1) * (ELin)(EE | m1)", + [{E4,[4]}], S), + {ok, _} = eval("(XXL)(Lin) (E | m1)", + [{{D1,D4},[4]},{{D1,D2},[1]},{{D2,D1},[2]},{{D2,D4},[5]}, + {{D3,D2},[3]},{{D6,D4},[7]},{{D5,D6},[6]}], S), + {ok, _} = eval("(XXL)(ELin) (EE | m1)", + [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, + {{D5,D4},[6]}], S), + {ok, _} = eval("(XXL)(Lin)(Fun)(Lin) (E | m1)", + [{{D1,D4},[4]},{{D1,D2},[1]},{{D2,D1},[2]},{{D2,D4},[5]}, + {{D3,D2},[3]},{{D6,D4},[7]},{{D5,D6},[6]}], S), + {ok, _} = eval("(XXL)(ELin)(Fun)(ELin) (EE | m1)", + [{{D1,D1},[1]},{{D1,D4},[1,4]},{{D3,D1},[3]},{{D3,D4},[3]}, + {{D5,D4},[6]}], S), %% A few tests on regexp. - ?line {ok, _} = eval("\"(foo\":Mod", parse_error, S), - ?line {ok, _} = eval("_Foo:_/_", parse_error, S), - ?line {ok, _} = eval("\".*foo\"", parse_error, S), - ?line {ok, _} = eval("_:_/_:Lin", parse_error, S), - ?line {ok, _} = eval("_:_/_:Mod", parse_error, S), - ?line {ok, _} = eval("_:_/_:App", parse_error, S), - ?line {ok, _} = eval("_:_/_:Rel", parse_error, S), - ?line {ok, _} = eval("m2:_/4", [F4], S), - ?line {ok, _} = eval("m2:_/4:Fun", [F4], S), - ?line {ok, _} = eval("\"m.?\":\"f.*\"/\"6\"", [F6], S), - ?line {ok, _} = eval("_:_/6", [F6], S), - ?line {ok, _} = eval("m1:\"f1\"/_", [F1], S), - ?line {ok, _} = eval("\"m1\":f1/_", [F1], S), - ?line {ok, _} = eval("\"m1\":Mod", [m1], S), - ?line {ok, _} = eval("\"a1\":App", [a1], S), - ?line {ok, _} = eval("\"r1\":Rel", [r1], S), - ?line {ok, _} = eval("_:_/-1", [], S), + {ok, _} = eval("\"(foo\":Mod", parse_error, S), + {ok, _} = eval("_Foo:_/_", parse_error, S), + {ok, _} = eval("\".*foo\"", parse_error, S), + {ok, _} = eval("_:_/_:Lin", parse_error, S), + {ok, _} = eval("_:_/_:Mod", parse_error, S), + {ok, _} = eval("_:_/_:App", parse_error, S), + {ok, _} = eval("_:_/_:Rel", parse_error, S), + {ok, _} = eval("m2:_/4", [F4], S), + {ok, _} = eval("m2:_/4:Fun", [F4], S), + {ok, _} = eval("\"m.?\":\"f.*\"/\"6\"", [F6], S), + {ok, _} = eval("_:_/6", [F6], S), + {ok, _} = eval("m1:\"f1\"/_", [F1], S), + {ok, _} = eval("\"m1\":f1/_", [F1], S), + {ok, _} = eval("\"m1\":Mod", [m1], S), + {ok, _} = eval("\"a1\":App", [a1], S), + {ok, _} = eval("\"r1\":Rel", [r1], S), + {ok, _} = eval("_:_/-1", [], S), ok. -loops(suite) -> []; -loops(doc) -> ["More Inter Call Graph, loops and \"unusual\" cases"]; +%% More Inter Call Graph, loops and "unusual" cases loops(Conf) when is_list(Conf) -> S0 = new(), @@ -627,51 +594,49 @@ loops(Conf) when is_list(Conf) -> LCallAt_m1 = [{E2,2},{E3,3},{E4,4}], XCallAt_m1 = [{E1,1},{E5,5}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), - ?line S = set_up(S1), + S = set_up(S1), % Neither F6 nor F7 is included. Perhaps one should change that? - ?line {ok, _} = eval("EE | m1", [E1,E2,{F3,F3}], S), - ?line {ok, _} = eval(f("(XXL)(ELin) (EE | ~p)", [F3]), [{{D3,D3},[3]}], S), + {ok, _} = eval("EE | m1", [E1,E2,{F3,F3}], S), + {ok, _} = eval(f("(XXL)(ELin) (EE | ~p)", [F3]), [{{D3,D3},[3]}], S), - ?line {ok, _} = eval("m1->m1 | m1->m1", type_error, S), - ?line {ok, _} = eval(f("~p | ~p", [F2, F1]), type_error, S), + {ok, _} = eval("m1->m1 | m1->m1", type_error, S), + {ok, _} = eval(f("~p | ~p", [F2, F1]), type_error, S), - ?line {ok, _} = eval(f("range (closure EE | ~p)", [F1]), [F1], S), - ?line {ok, _} = eval(f("domain (closure EE || ~p)", [F3]), [F3], S), + {ok, _} = eval(f("range (closure EE | ~p)", [F1]), [F1], S), + {ok, _} = eval(f("domain (closure EE || ~p)", [F3]), [F3], S), - ?line {ok, _} = eval(f("domain (closure E || ~p)", [F3]), [F3,F4,F5], S), + {ok, _} = eval(f("domain (closure E || ~p)", [F3]), [F3,F4,F5], S), - ?line {ok, _} = eval("components E", [[F1],[F2],[F3,F4,F5]], S), - ?line {ok, _} = eval("components EE", [[F1],[F2],[F3]], S), + {ok, _} = eval("components E", [[F1],[F2],[F3,F4,F5]], S), + {ok, _} = eval("components EE", [[F1],[F2],[F3]], S), ok. -no_data(suite) -> []; -no_data(doc) -> ["Simple tests when there is no data"]; +%% Simple tests when there is no data no_data(Conf) when is_list(Conf) -> S0 = new(), - ?line S1 = set_up(S0), - ?line {ok, _} = eval("M", [], S1), - ?line {ok, _} = eval("A", [], S1), - ?line {ok, _} = eval("R", [], S1), + S1 = set_up(S0), + {ok, _} = eval("M", [], S1), + {ok, _} = eval("A", [], S1), + {ok, _} = eval("R", [], S1), ModInfo = #xref_mod{name = m, app_name = []}, - ?line S2 = add_module(S1, ModInfo, [], [], [], [], [], []), + S2 = add_module(S1, ModInfo, [], [], [], [], [], []), AppInfo = #xref_app{name = a, rel_name = []}, - ?line S3 = add_application(S2, AppInfo), + S3 = add_application(S2, AppInfo), RelInfo = #xref_rel{name = r, dir = ""}, - ?line S4 = add_release(S3, RelInfo), - ?line S5 = set_up(S4), - ?line {ok, _} = eval("M", [m], S5), - ?line {ok, _} = eval("A", [a], S5), - ?line {ok, _} = eval("R", [r], S5), + S4 = add_release(S3, RelInfo), + S5 = set_up(S4), + {ok, _} = eval("M", [m], S5), + {ok, _} = eval("A", [a], S5), + {ok, _} = eval("R", [r], S5), ok. -modules(suite) -> []; -modules(doc) -> ["Modules mode"]; +%% Modules mode modules(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir, "rel2"), @@ -684,34 +649,33 @@ modules(Conf) when is_list(Conf) -> Xbeam = fname(EB2, "x.beam"), Ybeam = fname(EB1_1, "y.beam"), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), - ?line {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), - - ?line {ok, S0} = xref_base:new([{xref_mode, modules}]), - ?line {ok, release2, S1} = - xref_base:add_release(S0, Dir, [{name,release2}]), - ?line S = set_up(S1), - ?line {{error, _, {unavailable_analysis, undefined_function_calls}}, _} = - xref_base:analyze(S, undefined_function_calls), - ?line {{error, _, {unavailable_analysis, locals_not_used}}, _} = - xref_base:analyze(S, locals_not_used), - ?line {{error, _, {unavailable_analysis, {call, foo}}}, _} = - xref_base:analyze(S, {call, foo}), - ?line {{error, _, {unavailable_analysis, {use, foo}}}, _} = - xref_base:analyze(S, {use, foo}), - ?line analyze(undefined_functions, [{x,undef,0}], S), - ?line 5 = length(xref_base:info(S)), + {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), + {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), + + {ok, S0} = xref_base:new([{xref_mode, modules}]), + {ok, release2, S1} = + xref_base:add_release(S0, Dir, [{name,release2}]), + S = set_up(S1), + {{error, _, {unavailable_analysis, undefined_function_calls}}, _} = + xref_base:analyze(S, undefined_function_calls), + {{error, _, {unavailable_analysis, locals_not_used}}, _} = + xref_base:analyze(S, locals_not_used), + {{error, _, {unavailable_analysis, {call, foo}}}, _} = + xref_base:analyze(S, {call, foo}), + {{error, _, {unavailable_analysis, {use, foo}}}, _} = + xref_base:analyze(S, {use, foo}), + analyze(undefined_functions, [{x,undef,0}], S), + 5 = length(xref_base:info(S)), %% More: all info, conversions. - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), - ?line ok = xref_base:delete(S), + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), + ok = xref_base:delete(S), ok. -add(suite) -> []; -add(doc) -> ["Add modules, applications, releases, directories"]; +%% Add modules, applications, releases, directories add(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir, "rel2"), @@ -727,116 +691,114 @@ add(Conf) when is_list(Conf) -> Xbeam = fname(EB2, "x.beam"), Ybeam = fname(EB1_1, "y.beam"), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), - ?line {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), - - ?line case os:type() of - {unix, _} -> - ?line make_udir(UDir), - ?line make_ufile(UFile); - _ -> - true - end, - - ?line {error, _, {invalid_options,[not_an_option] }} = - xref_base:new([not_an_option]), - ?line {error, _, {invalid_options,[{verbose,not_a_value}] }} = - xref_base:new([{verbose,not_a_value}]), - ?line S = new(), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref_base:set_up(S, [not_an_option]), - ?line {error, _, {invalid_options,[{builtins,true},not_an_option]}} = - xref_base:add_directory(S, foo, [{builtins,true},not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref_base:add_directory(S, foo, [{builtins,not_a_value}]), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref_base:add_directory(S, {foo,bar}, []), - ?line {error, _, {invalid_options,[{builtins,true},not_an_option]}} = - xref_base:add_module(S, foo, [{builtins,true},not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref_base:add_module(S, foo, [{builtins,not_a_value}]), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref_base:add_module(S, {foo,bar}, []), - ?line {error, _, {invalid_options,[{builtins,true},not_an_option]}} = - xref_base:add_application(S, foo, [{builtins,true},not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref_base:add_application(S, foo, [{builtins,not_a_value}]), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref_base:add_application(S, {foo,bar}, []), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref_base:add_release(S, foo, [not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref_base:add_release(S, foo, [{builtins,not_a_value}]), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref_base:add_release(S, {foo,bar}, []), - ?line {ok, S1} = - xref_base:set_default(S, [{verbose,false}, {warnings, false}]), - ?line case os:type() of - {unix, _} -> - ?line {error, _, {file_error, _, _}} = - xref_base:add_release(S, UDir); - _ -> - true - end, - ?line {error, _, {file_error, _, _}} = - xref_base:add_release(S, fname(["/a/b/c/d/e/f","__foo"])), - ?line {ok, release2, S2} = - xref_base:add_release(S1, Dir, [{name,release2}]), - ?line {error, _, {module_clash, {x, _, _}}} = - xref_base:add_module(S2, Xbeam), - ?line {ok, S3} = xref_base:remove_release(S2, release2), - ?line {ok, rel2, S4} = xref_base:add_release(S3, Dir), - ?line {error, _, {release_clash, {rel2, _, _}}} = - xref_base:add_release(S4, Dir), - ?line {ok, S5} = xref_base:remove_release(S4, rel2), + {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), + {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), + + case os:type() of + {unix, _} -> + make_udir(UDir), + make_ufile(UFile); + _ -> + true + end, + + {error, _, {invalid_options,[not_an_option] }} = + xref_base:new([not_an_option]), + {error, _, {invalid_options,[{verbose,not_a_value}] }} = + xref_base:new([{verbose,not_a_value}]), + S = new(), + {error, _, {invalid_options,[not_an_option]}} = + xref_base:set_up(S, [not_an_option]), + {error, _, {invalid_options,[{builtins,true},not_an_option]}} = + xref_base:add_directory(S, foo, [{builtins,true},not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref_base:add_directory(S, foo, [{builtins,not_a_value}]), + {error, _, {invalid_filename,{foo,bar}}} = + xref_base:add_directory(S, {foo,bar}, []), + {error, _, {invalid_options,[{builtins,true},not_an_option]}} = + xref_base:add_module(S, foo, [{builtins,true},not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref_base:add_module(S, foo, [{builtins,not_a_value}]), + {error, _, {invalid_filename,{foo,bar}}} = + xref_base:add_module(S, {foo,bar}, []), + {error, _, {invalid_options,[{builtins,true},not_an_option]}} = + xref_base:add_application(S, foo, [{builtins,true},not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref_base:add_application(S, foo, [{builtins,not_a_value}]), + {error, _, {invalid_filename,{foo,bar}}} = + xref_base:add_application(S, {foo,bar}, []), + {error, _, {invalid_options,[not_an_option]}} = + xref_base:add_release(S, foo, [not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref_base:add_release(S, foo, [{builtins,not_a_value}]), + {error, _, {invalid_filename,{foo,bar}}} = + xref_base:add_release(S, {foo,bar}, []), + {ok, S1} = + xref_base:set_default(S, [{verbose,false}, {warnings, false}]), + case os:type() of + {unix, _} -> + {error, _, {file_error, _, _}} = + xref_base:add_release(S, UDir); + _ -> + true + end, + {error, _, {file_error, _, _}} = + xref_base:add_release(S, fname(["/a/b/c/d/e/f","__foo"])), + {ok, release2, S2} = + xref_base:add_release(S1, Dir, [{name,release2}]), + {error, _, {module_clash, {x, _, _}}} = + xref_base:add_module(S2, Xbeam), + {ok, S3} = xref_base:remove_release(S2, release2), + {ok, rel2, S4} = xref_base:add_release(S3, Dir), + {error, _, {release_clash, {rel2, _, _}}} = + xref_base:add_release(S4, Dir), + {ok, S5} = xref_base:remove_release(S4, rel2), %% One unreadable file and one JAM file found (no verification here): - ?line {ok, [], S6} = xref_base:add_directory(S5, fname(CopyDir,"dir"), - [{recurse,true}, {warnings,true}]), - ?line case os:type() of - {unix, _} -> - ?line {error, _, {file_error, _, _}} = - xref_base:add_directory(S6, UDir); - _ -> - true - end, - ?line {ok, app1, S7} = xref_base:add_application(S6, A1_1), - ?line {error, _, {application_clash, {app1, _, _}}} = - xref_base:add_application(S7, A1_1), - ?line {ok, S8} = xref_base:remove_application(S7, app1), - ?line ok = xref_base:delete(S8), - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), - ?line case os:type() of - {unix, _} -> - ?line ok = file:del_dir(UDir), - ?line ok = file:delete(UFile); - _ -> - true - end, + {ok, [], S6} = xref_base:add_directory(S5, fname(CopyDir,"dir"), + [{recurse,true}, {warnings,true}]), + case os:type() of + {unix, _} -> + {error, _, {file_error, _, _}} = + xref_base:add_directory(S6, UDir); + _ -> + true + end, + {ok, app1, S7} = xref_base:add_application(S6, A1_1), + {error, _, {application_clash, {app1, _, _}}} = + xref_base:add_application(S7, A1_1), + {ok, S8} = xref_base:remove_application(S7, app1), + ok = xref_base:delete(S8), + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), + case os:type() of + {unix, _} -> + ok = file:del_dir(UDir), + ok = file:delete(UFile); + _ -> + true + end, ok. -default(suite) -> []; -default(doc) -> ["Default values of options"]; +%% Default values of options default(Conf) when is_list(Conf) -> S = new(), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref_base:set_default(S, not_an_option, true), - ?line {error, _, {invalid_options,[{builtins, not_a_value}]}} = - xref_base:set_default(S, builtins, not_a_value), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref_base:get_default(S, not_an_option), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref_base:set_default(S, [not_an_option]), - - ?line D = xref_base:get_default(S), - ?line [{builtins,false},{recurse,false},{verbose,false},{warnings,true}] = - D, - - ?line ok = xref_base:delete(S), + {error, _, {invalid_options,[not_an_option]}} = + xref_base:set_default(S, not_an_option, true), + {error, _, {invalid_options,[{builtins, not_a_value}]}} = + xref_base:set_default(S, builtins, not_a_value), + {error, _, {invalid_options,[not_an_option]}} = + xref_base:get_default(S, not_an_option), + {error, _, {invalid_options,[not_an_option]}} = + xref_base:set_default(S, [not_an_option]), + + D = xref_base:get_default(S), + [{builtins,false},{recurse,false},{verbose,false},{warnings,true}] = + D, + + ok = xref_base:delete(S), ok. -info(suite) -> []; -info(doc) -> ["The info functions"]; +%% The info functions info(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"rel2"), @@ -850,197 +812,195 @@ info(Conf) when is_list(Conf) -> Xbeam = fname(EB2, "x.beam"), Ybeam = fname(EB1_1, "y.beam"), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), - ?line {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), - - ?line {ok, _} = start(s), - ?line {error, _, {no_such_info, release}} = xref:info(s, release), - ?line {error, _, {no_such_info, release}} = xref:info(s, release, rel), - ?line {error, _, {no_such_module, mod}} = xref:info(s, modules, mod), - ?line {error, _, {no_such_application, app}} = - xref:info(s, applications, app), - ?line {error, _, {no_such_release, rel}} = xref:info(s, releases, rel), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), - ?line {ok, rel2} = xref:add_release(s, Dir), - ?line 9 = length(xref:info(s)), - ?line [{x,_}, {y, _}] = xref:info(s, modules), - ?line [{app1,_}, {app2, _}] = xref:info(s, applications), - ?line [{rel2,_}] = xref:info(s, releases), - ?line [] = xref:info(s, libraries), - ?line [{x,_}] = xref:info(s, modules, x), - ?line [{rel2,_}] = xref:info(s, releases, rel2), - ?line {error, _, {no_such_library, foo}} = xref:info(s, libraries, [foo]), - - ?line {ok, lib1} = - compile:file(fname(LDir,lib1),[debug_info,{outdir,LDir}]), - ?line {ok, lib2} = - compile:file(fname(LDir,lib2),[debug_info,{outdir,LDir}]), - ?line ok = xref:set_library_path(s, [LDir], [{verbose,false}]), - ?line [{lib1,_}, {lib2, _}] = xref:info(s, libraries), - ?line [{lib1,_}, {lib2, _}] = xref:info(s, libraries, [lib1,lib2]), - ?line ok = file:delete(fname(LDir, "lib1.beam")), - ?line ok = file:delete(fname(LDir, "lib2.beam")), - - ?line check_state(s), - - ?line xref:stop(s), - - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), + {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), + {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), + + {ok, _} = start(s), + {error, _, {no_such_info, release}} = xref:info(s, release), + {error, _, {no_such_info, release}} = xref:info(s, release, rel), + {error, _, {no_such_module, mod}} = xref:info(s, modules, mod), + {error, _, {no_such_application, app}} = + xref:info(s, applications, app), + {error, _, {no_such_release, rel}} = xref:info(s, releases, rel), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, rel2} = xref:add_release(s, Dir), + 9 = length(xref:info(s)), + [{x,_}, {y, _}] = xref:info(s, modules), + [{app1,_}, {app2, _}] = xref:info(s, applications), + [{rel2,_}] = xref:info(s, releases), + [] = xref:info(s, libraries), + [{x,_}] = xref:info(s, modules, x), + [{rel2,_}] = xref:info(s, releases, rel2), + {error, _, {no_such_library, foo}} = xref:info(s, libraries, [foo]), + + {ok, lib1} = + compile:file(fname(LDir,lib1),[debug_info,{outdir,LDir}]), + {ok, lib2} = + compile:file(fname(LDir,lib2),[debug_info,{outdir,LDir}]), + ok = xref:set_library_path(s, [LDir], [{verbose,false}]), + [{lib1,_}, {lib2, _}] = xref:info(s, libraries), + [{lib1,_}, {lib2, _}] = xref:info(s, libraries, [lib1,lib2]), + ok = file:delete(fname(LDir, "lib1.beam")), + ok = file:delete(fname(LDir, "lib2.beam")), + + check_state(s), + + xref:stop(s), + + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), ok. -lib(suite) -> []; -lib(doc) -> ["Library modules"]; +%% Library modules lib(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"lib_test"), UDir = fname([CopyDir,"dir","non_existent"]), - ?line {ok, lib1} = compile:file(fname(Dir,lib1),[debug_info,{outdir,Dir}]), - ?line {ok, lib2} = compile:file(fname(Dir,lib2),[debug_info,{outdir,Dir}]), - ?line {ok, lib3} = compile:file(fname(Dir,lib3),[debug_info,{outdir,Dir}]), - ?line {ok, t} = compile:file(fname(Dir,t),[debug_info,{outdir,Dir}]), - - ?line {ok, _} = start(s), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), - ?line {ok, t} = xref:add_module(s, fname(Dir,"t.beam")), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref:set_library_path(s, ["foo"], [not_an_option]), - ?line {error, _, {invalid_path,otp}} = xref:set_library_path(s,otp), - ?line {error, _, {invalid_path,[""]}} = xref:set_library_path(s,[""]), - ?line {error, _, {invalid_path,[[$a | $b]]}} = - xref:set_library_path(s,[[$a | $b]]), - ?line {error, _, {invalid_path,[otp]}} = xref:set_library_path(s,[otp]), - ?line {ok, []} = xref:get_library_path(s), - ?line ok = xref:set_library_path(s, [Dir], [{verbose,false}]), - ?line {ok, UnknownFunctions} = xref:q(s, "U"), - ?line [{lib1,unknown,0}, {lib2,local,0}, - {lib2,unknown,0}, {unknown,unknown,0}] - = UnknownFunctions, - ?line {ok, [{lib2,f,0},{lib3,f,0}]} = xref:q(s, "DF"), - ?line {ok, []} = xref:q(s, "DF_1"), - ?line {ok, [{lib2,f,0}]} = xref:q(s, "DF_2"), - ?line {ok, [{lib2,f,0}]} = xref:q(s, "DF_3"), - - ?line {ok, [unknown]} = xref:q(s, "UM"), - ?line {ok, UnknownDefAt} = xref:q(s, "(Lin)U"), - ?line [{{lib1,unknown,0},0},{{lib2,local,0},0}, {{lib2,unknown,0},0}, - {{unknown,unknown,0},0}] = UnknownDefAt, - ?line {ok, LibFuns} = xref:q(s, "X * LM"), - ?line [{lib2,f,0},{lib3,f,0}] = LibFuns, - ?line {ok, LibMods} = xref:q(s, "LM"), - ?line [lib1,lib2,lib3] = LibMods, - ?line {ok, [{{lib2,f,0},0},{{lib3,f,0},0}]} = xref:q(s, "(Lin) (LM * X)"), - ?line {ok, [{{lib1,unknown,0},0}, {{lib2,f,0},0}, {{lib2,local,0},0}, - {{lib2,unknown,0},0}, {{lib3,f,0},0}]} = xref:q(s,"(Lin)LM"), - ?line {ok,[lib1,lib2,lib3,t,unknown]} = xref:q(s,"M"), - ?line {ok,[{lib2,f,0},{lib3,f,0},{t,t,0}]} = xref:q(s,"X * M"), - ?line check_state(s), - - ?line copy_file(fname(Dir, "lib1.erl"), fname(Dir,"lib1.beam")), - ?line ok = xref:set_library_path(s, [Dir]), - ?line {error, _, _} = xref:q(s, "U"), + {ok, lib1} = compile:file(fname(Dir,lib1),[debug_info,{outdir,Dir}]), + {ok, lib2} = compile:file(fname(Dir,lib2),[debug_info,{outdir,Dir}]), + {ok, lib3} = compile:file(fname(Dir,lib3),[debug_info,{outdir,Dir}]), + {ok, t} = compile:file(fname(Dir,t),[debug_info,{outdir,Dir}]), + + {ok, _} = start(s), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, t} = xref:add_module(s, fname(Dir,"t.beam")), + {error, _, {invalid_options,[not_an_option]}} = + xref:set_library_path(s, ["foo"], [not_an_option]), + {error, _, {invalid_path,otp}} = xref:set_library_path(s,otp), + {error, _, {invalid_path,[""]}} = xref:set_library_path(s,[""]), + {error, _, {invalid_path,[[$a | $b]]}} = + xref:set_library_path(s,[[$a | $b]]), + {error, _, {invalid_path,[otp]}} = xref:set_library_path(s,[otp]), + {ok, []} = xref:get_library_path(s), + ok = xref:set_library_path(s, [Dir], [{verbose,false}]), + {ok, UnknownFunctions} = xref:q(s, "U"), + [{lib1,unknown,0}, {lib2,local,0}, + {lib2,unknown,0}, {unknown,unknown,0}] + = UnknownFunctions, + {ok, [{lib2,f,0},{lib3,f,0}]} = xref:q(s, "DF"), + {ok, []} = xref:q(s, "DF_1"), + {ok, [{lib2,f,0}]} = xref:q(s, "DF_2"), + {ok, [{lib2,f,0}]} = xref:q(s, "DF_3"), + + {ok, [unknown]} = xref:q(s, "UM"), + {ok, UnknownDefAt} = xref:q(s, "(Lin)U"), + [{{lib1,unknown,0},0},{{lib2,local,0},0}, {{lib2,unknown,0},0}, + {{unknown,unknown,0},0}] = UnknownDefAt, + {ok, LibFuns} = xref:q(s, "X * LM"), + [{lib2,f,0},{lib3,f,0}] = LibFuns, + {ok, LibMods} = xref:q(s, "LM"), + [lib1,lib2,lib3] = LibMods, + {ok, [{{lib2,f,0},0},{{lib3,f,0},0}]} = xref:q(s, "(Lin) (LM * X)"), + {ok, [{{lib1,unknown,0},0}, {{lib2,f,0},0}, {{lib2,local,0},0}, + {{lib2,unknown,0},0}, {{lib3,f,0},0}]} = xref:q(s,"(Lin)LM"), + {ok,[lib1,lib2,lib3,t,unknown]} = xref:q(s,"M"), + {ok,[{lib2,f,0},{lib3,f,0},{t,t,0}]} = xref:q(s,"X * M"), + check_state(s), + + copy_file(fname(Dir, "lib1.erl"), fname(Dir,"lib1.beam")), + ok = xref:set_library_path(s, [Dir]), + {error, _, _} = xref:q(s, "U"), %% OTP-3921. AM and LM not always disjoint. - ?line {ok, lib1} = compile:file(fname(Dir,lib1),[debug_info,{outdir,Dir}]), - ?line {ok, lib1} = xref:add_module(s, fname(Dir,"lib1.beam")), - ?line check_state(s), - - ?line {error, _, {file_error, _, _}} = xref:set_library_path(s, [UDir]), - - ?line xref:stop(s), - ?line ok = file:delete(fname(Dir, "lib1.beam")), - ?line ok = file:delete(fname(Dir, "lib2.beam")), - ?line ok = file:delete(fname(Dir, "lib3.beam")), - ?line ok = file:delete(fname(Dir, "t.beam")), - - ?line {ok, cp} = compile:file(fname(Dir,cp),[debug_info,{outdir,Dir}]), - ?line {ok, _} = start(s), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), - ?line {ok, cp} = xref:add_module(s, fname(Dir,"cp.beam")), - ?line {ok, [{lists, sort, 1}]} = xref:q(s, "U"), - ?line ok = xref:set_library_path(s, code_path), - ?line {ok, []} = xref:q(s, "U"), - ?line check_state(s), - ?line xref:stop(s), - ?line ok = file:delete(fname(Dir, "cp.beam")), + {ok, lib1} = compile:file(fname(Dir,lib1),[debug_info,{outdir,Dir}]), + {ok, lib1} = xref:add_module(s, fname(Dir,"lib1.beam")), + check_state(s), + + {error, _, {file_error, _, _}} = xref:set_library_path(s, [UDir]), + + xref:stop(s), + ok = file:delete(fname(Dir, "lib1.beam")), + ok = file:delete(fname(Dir, "lib2.beam")), + ok = file:delete(fname(Dir, "lib3.beam")), + ok = file:delete(fname(Dir, "t.beam")), + + {ok, cp} = compile:file(fname(Dir,cp),[debug_info,{outdir,Dir}]), + {ok, _} = start(s), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, cp} = xref:add_module(s, fname(Dir,"cp.beam")), + {ok, [{lists, sort, 1}]} = xref:q(s, "U"), + ok = xref:set_library_path(s, code_path), + {ok, []} = xref:q(s, "U"), + check_state(s), + xref:stop(s), + ok = file:delete(fname(Dir, "cp.beam")), ok. -read(suite) -> []; -read(doc) -> ["Data read from the Abstract Code"]; +%% Data read from the Abstract Code read(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"read"), File = fname(Dir, "read"), Beam = fname(Dir, "read.beam"), - ?line {ok, read} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line do_read(File, abstract_v2), - ?line copy_file(fname(Dir, "read.beam.v1"), Beam), - ?line do_read(File, abstract_v1), - ?line ok = file:delete(Beam), + {ok, read} = compile:file(File, [debug_info,{outdir,Dir}]), + do_read(File, abstract_v2), + copy_file(fname(Dir, "read.beam.v1"), Beam), + do_read(File, abstract_v1), + ok = file:delete(Beam), ok. do_read(File, Version) -> - ?line {ok, _} = start(s), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), - ?line {ok, read} = xref:add_module(s, File), + {ok, _} = start(s), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, read} = xref:add_module(s, File), - ?line {U, OK, OKB} = read_expected(Version), + {U, OK, OKB} = read_expected(Version), %% {ok, UC} = xref:q(s, "(Lin) UC"), %% RR = to_external(converse(family_to_relation(family(UC)))), %% lists:foreach(fun(X) -> io:format("~w~n", [X]) end, RR), Unres = to_external(relation_to_family(converse(from_term(U)))), - ?line {ok, Unres} = xref:q(s, "(Lin) UC"), + {ok, Unres} = xref:q(s, "(Lin) UC"), %% {ok, EE} = xref:q(s, "(Lin) (E - UC)"), %% AA = to_external(converse(family_to_relation(family(EE)))), %% lists:foreach(fun(X) -> io:format("~w~n", [X]) end, AA), Calls = to_external(relation_to_family(converse(from_term(OK)))), - ?line {ok, Calls} = xref:q(s, "(Lin) (E - UC) "), - - ?line ok = check_state(s), - ?line {ok, UM} = xref:q(s, "UM"), - ?line true = member('$M_EXPR', UM), - - ?line {ok, X} = xref:q(s, "X"), - ?line true = member({read, module_info, 0}, X), - ?line false = member({foo, module_info, 0}, X), - ?line false = member({erlang, module_info, 0}, X), - ?line {ok, Unknowns} = xref:q(s, "U"), - ?line false = member({read, module_info, 0}, Unknowns), - ?line true = member({foo, module_info, 0}, Unknowns), - ?line true = member({erlang, module_info, 0}, Unknowns), - ?line {ok, LC} = xref:q(s, "LC"), - ?line true = member({{read,bi,0},{read,bi,0}}, LC), - - ?line ok = xref:set_library_path(s, add_erts_code_path(fname(code:lib_dir(kernel),ebin))), - ?line io:format("~p~n",[(catch xref:get_library_path(s))]), - ?line {ok, X2} = xref:q(s, "X"), - ?line ok = check_state(s), - ?line true = member({read, module_info, 0}, X2), - ?line false = member({foo, module_info, 0}, X2), - ?line true = member({erlang, module_info, 0}, X2), - ?line {ok, Unknowns2} = xref:q(s, "U"), - ?line false = member({read, module_info, 0}, Unknowns2), - ?line true = member({foo, module_info, 0}, Unknowns2), - ?line false = member({erlang, module_info, 0}, Unknowns2), - - ?line ok = xref:remove_module(s, read), - ?line {ok, read} = xref:add_module(s, File, [{builtins,true}]), + {ok, Calls} = xref:q(s, "(Lin) (E - UC) "), + + ok = check_state(s), + {ok, UM} = xref:q(s, "UM"), + true = member('$M_EXPR', UM), + + {ok, X} = xref:q(s, "X"), + true = member({read, module_info, 0}, X), + false = member({foo, module_info, 0}, X), + false = member({erlang, module_info, 0}, X), + {ok, Unknowns} = xref:q(s, "U"), + false = member({read, module_info, 0}, Unknowns), + true = member({foo, module_info, 0}, Unknowns), + true = member({erlang, module_info, 0}, Unknowns), + {ok, LC} = xref:q(s, "LC"), + true = member({{read,bi,0},{read,bi,0}}, LC), + + ok = xref:set_library_path(s, add_erts_code_path(fname(code:lib_dir(kernel),ebin))), + io:format("~p~n",[(catch xref:get_library_path(s))]), + {ok, X2} = xref:q(s, "X"), + ok = check_state(s), + true = member({read, module_info, 0}, X2), + false = member({foo, module_info, 0}, X2), + true = member({erlang, module_info, 0}, X2), + {ok, Unknowns2} = xref:q(s, "U"), + false = member({read, module_info, 0}, Unknowns2), + true = member({foo, module_info, 0}, Unknowns2), + false = member({erlang, module_info, 0}, Unknowns2), + + ok = xref:remove_module(s, read), + {ok, read} = xref:add_module(s, File, [{builtins,true}]), UnresB = to_external(relation_to_family(converse(from_term(U)))), - ?line {ok, UnresB} = xref:q(s, "(Lin) UC"), + {ok, UnresB} = xref:q(s, "(Lin) UC"), CallsB = to_external(relation_to_family(converse(from_term(OKB)))), - ?line {ok, CallsB} = xref:q(s, "(Lin) (E - UC) "), - ?line ok = check_state(s), - ?line {ok, XU} = xref:q(s, "XU"), - ?line Erl = set([{erlang,length,1},{erlang,integer,1}, - {erlang,binary_to_term,1}]), - ?line [{erlang,binary_to_term,1},{erlang,length,1}] = - to_external(intersection(set(XU), Erl)), - ?line xref:stop(s). + {ok, CallsB} = xref:q(s, "(Lin) (E - UC) "), + ok = check_state(s), + {ok, XU} = xref:q(s, "XU"), + Erl = set([{erlang,length,1},{erlang,integer,1}, + {erlang,binary_to_term,1}]), + [{erlang,binary_to_term,1},{erlang,length,1}] = + to_external(intersection(set(XU), Erl)), + xref:stop(s). %% What is expected when xref_SUITE_data/read/read.erl is added: read_expected(Version) -> @@ -1052,172 +1012,172 @@ read_expected(Version) -> FF = {read,funfuns,0}, U = [{POS1+5,{FF,{dist,'$F_EXPR',0}}}, - {POS1+8,{FF,{dist,'$F_EXPR',0}}}, - {POS2+8,{{read,funfuns,0},{expr,'$F_EXPR',1}}}, - {POS3+4,{FF,{expr,'$F_EXPR',2}}}, - {POS4+2,{FF,{modul,'$F_EXPR',1}}}, - {POS4+4,{FF,{spm,'$F_EXPR',1}}}, - {POS4+6,{FF,{spm,'$F_EXPR',1}}}, - {POS4+8,{FF,{spm,'$F_EXPR',1}}}, - {POS5+1,{FF,{'$M_EXPR','$F_EXPR',0}}}, - {POS5+2,{FF,{'$M_EXPR','$F_EXPR',0}}}, - {POS5+3,{FF,{'$M_EXPR','$F_EXPR',0}}}, - {POS6+1,{FF,{'$M_EXPR','$F_EXPR',0}}}, - {POS6+2,{FF,{'$M_EXPR','$F_EXPR',0}}}, - {POS6+4,{FF,{n,'$F_EXPR',-1}}}, - {POS7+1,{FF,{'$M_EXPR',f,1}}}, - {POS7+2,{FF,{'$M_EXPR',f,1}}}, - {POS8+2,{FF,{hej,'$F_EXPR',1}}}, - {POS8+3,{FF,{t,'$F_EXPR',1}}}, - {POS8+5,{FF,{a,'$F_EXPR',1}}}, - {POS8+7,{FF,{m,'$F_EXPR',1}}}, - {POS9+1,{FF,{'$M_EXPR',f,1}}}, - {POS9+3,{FF,{a,'$F_EXPR',1}}}, - {POS10+1,{FF,{'$M_EXPR',foo,1}}}, - {POS10+2,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS10+3,{FF,{'$M_EXPR','$F_EXPR',2}}}, - {POS10+4,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS10+5,{FF,{'$M_EXPR',san,1}}}, - {POS10+6,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS11+1,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS11+2,{FF,{'$M_EXPR','$F_EXPR',-1}}}, - {POS11+3,{FF,{m,f,-1}}}, - {POS11+4,{FF,{m,f,-1}}}, - {POS11+5,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS11+6,{FF,{'$M_EXPR','$F_EXPR',1}}}, - {POS12+1,{FF,{'$M_EXPR','$F_EXPR',-1}}}, - {POS12+4,{FF,{'$M_EXPR','$F_EXPR',2}}}, - {POS12+7,{FF,{'$M_EXPR','$F_EXPR',-1}}}, - {POS12+8,{FF,{m4,f4,-1}}}, - {POS13+2,{FF,{debug,'$F_EXPR',0}}}, - {POS13+3,{FF,{'$M_EXPR','$F_EXPR',-1}}}, - {POS14+8,{{read,bi,0},{'$M_EXPR','$F_EXPR',1}}}], + {POS1+8,{FF,{dist,'$F_EXPR',0}}}, + {POS2+8,{{read,funfuns,0},{expr,'$F_EXPR',1}}}, + {POS3+4,{FF,{expr,'$F_EXPR',2}}}, + {POS4+2,{FF,{modul,'$F_EXPR',1}}}, + {POS4+4,{FF,{spm,'$F_EXPR',1}}}, + {POS4+6,{FF,{spm,'$F_EXPR',1}}}, + {POS4+8,{FF,{spm,'$F_EXPR',1}}}, + {POS5+1,{FF,{'$M_EXPR','$F_EXPR',0}}}, + {POS5+2,{FF,{'$M_EXPR','$F_EXPR',0}}}, + {POS5+3,{FF,{'$M_EXPR','$F_EXPR',0}}}, + {POS6+1,{FF,{'$M_EXPR','$F_EXPR',0}}}, + {POS6+2,{FF,{'$M_EXPR','$F_EXPR',0}}}, + {POS6+4,{FF,{n,'$F_EXPR',-1}}}, + {POS7+1,{FF,{'$M_EXPR',f,1}}}, + {POS7+2,{FF,{'$M_EXPR',f,1}}}, + {POS8+2,{FF,{hej,'$F_EXPR',1}}}, + {POS8+3,{FF,{t,'$F_EXPR',1}}}, + {POS8+5,{FF,{a,'$F_EXPR',1}}}, + {POS8+7,{FF,{m,'$F_EXPR',1}}}, + {POS9+1,{FF,{'$M_EXPR',f,1}}}, + {POS9+3,{FF,{a,'$F_EXPR',1}}}, + {POS10+1,{FF,{'$M_EXPR',foo,1}}}, + {POS10+2,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS10+3,{FF,{'$M_EXPR','$F_EXPR',2}}}, + {POS10+4,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS10+5,{FF,{'$M_EXPR',san,1}}}, + {POS10+6,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS11+1,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS11+2,{FF,{'$M_EXPR','$F_EXPR',-1}}}, + {POS11+3,{FF,{m,f,-1}}}, + {POS11+4,{FF,{m,f,-1}}}, + {POS11+5,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS11+6,{FF,{'$M_EXPR','$F_EXPR',1}}}, + {POS12+1,{FF,{'$M_EXPR','$F_EXPR',-1}}}, + {POS12+4,{FF,{'$M_EXPR','$F_EXPR',2}}}, + {POS12+7,{FF,{'$M_EXPR','$F_EXPR',-1}}}, + {POS12+8,{FF,{m4,f4,-1}}}, + {POS13+2,{FF,{debug,'$F_EXPR',0}}}, + {POS13+3,{FF,{'$M_EXPR','$F_EXPR',-1}}}, + {POS14+8,{{read,bi,0},{'$M_EXPR','$F_EXPR',1}}}], O1 = [{20,{{read,lc,0},{ets,new,0}}}, - {21,{{read,lc,0},{ets,tab2list,1}}}, - {POS1+1,{FF,{erlang,spawn,1}}}, - {POS1+1,{FF,{mod17,fun17,0}}}, - {POS1+2,{FF,{erlang,spawn,1}}}, - {POS1+2,{FF,{read,local,0}}}, - {POS1+3,{FF,{erlang,spawn,1}}}, - {POS1+4,{FF,{dist,func,0}}}, - {POS1+4,{FF,{erlang,spawn,1}}}, - {POS1+5,{FF,{erlang,spawn,1}}}, - {POS1+6,{FF,{erlang,spawn_link,1}}}, - {POS1+6,{FF,{mod17,fun17,0}}}, - {POS1+7,{FF,{dist,func,0}}}, - {POS1+7,{FF,{erlang,spawn_link,1}}}, - {POS1+8,{FF,{erlang,spawn_link,1}}}, - {POS2+1,{FF,{d,f,0}}}, - {POS2+1,{FF,{dist,func,2}}}, - {POS2+1,{FF,{erlang,spawn,2}}}, - {POS2+2,{FF,{dist,func,2}}}, - {POS2+2,{FF,{erlang,spawn,2}}}, - {POS2+2,{FF,{mod42,func,0}}}, - {POS2+3,{FF,{d,f,0}}}, - {POS2+3,{FF,{dist,func,2}}}, - {POS2+3,{FF,{erlang,spawn_link,2}}}, - {POS2+4,{FF,{dist,func,2}}}, - {POS2+4,{FF,{erlang,spawn_link,2}}}, - {POS2+4,{FF,{mod42,func,0}}}, - {POS3+1,{FF,{dist,func,2}}}, - {POS3+3,{FF,{dist,func,2}}}, - {POS4+1,{FF,{erlang,spawn,4}}}, - {POS4+1,{FF,{modul,function,0}}}, - {POS4+2,{FF,{erlang,spawn,4}}}, - {POS4+3,{FF,{dist,func,2}}}, - {POS4+3,{FF,{erlang,spawn,4}}}, - {POS4+3,{FF,{spm,spf,2}}}, - {POS4+4,{FF,{dist,func,2}}}, - {POS4+4,{FF,{erlang,spawn,4}}}, - {POS4+5,{FF,{dist,func,2}}}, - {POS4+5,{FF,{erlang,spawn_link,4}}}, - {POS4+5,{FF,{spm,spf,2}}}, - {POS4+6,{FF,{dist,func,2}}}, - {POS4+6,{FF,{erlang,spawn_link,4}}}, - {POS4+7,{FF,{erlang,spawn_opt,4}}}, - {POS4+7,{FF,{read,bi,0}}}, - {POS4+7,{FF,{spm,spf,2}}}, - {POS4+8,{FF,{erlang,spawn_opt,4}}}, - {POS4+8,{FF,{read,bi,0}}}, - {POS5+1,{FF,{erlang,spawn,1}}}, - {POS5+2,{FF,{erlang,spawn,1}}}, - {POS5+3,{FF,{erlang,spawn_link,1}}}, - {POS6+1,{FF,{erlang,spawn,2}}}, - {POS6+2,{FF,{erlang,spawn_link,2}}}, - {POS7+1,{FF,{erlang,spawn,4}}}, - {POS7+2,{FF,{erlang,spawn_opt,4}}}, - {POS8+1,{FF,{hej,san,1}}}, - {POS8+4,{FF,{a,b,1}}}, - {POS8+4,{FF,{erlang,apply,2}}}, - {POS8+5,{FF,{erlang,apply,2}}}, - {POS8+6,{FF,{m,f,1}}}, - {POS9+1,{FF,{read,bi,0}}}, - {POS9+2,{FF,{a,b,1}}}, - {POS9+2,{FF,{erlang,apply,2}}}, - {POS9+3,{FF,{erlang,apply,2}}}, - {POS9+4,{FF,{erlang,apply,2}}}, - {POS9+4,{FF,{erlang,not_a_function,1}}}, - {POS9+5,{FF,{mod,func,2}}}, - {POS9+6,{FF,{erlang,apply,1}}}, - {POS9+7,{FF,{erlang,apply,2}}}, - {POS9+7,{FF,{math,add3,1}}}, - {POS9+8,{FF,{q,f,1}}}, - {POS10+4,{FF,{erlang,apply,2}}}, - {POS10+5,{FF,{mod1,fun1,1}}}, - {POS11+6,{FF,{erlang,apply,2}}}, - {POS12+1,{FF,{erlang,apply,2}}}, - {POS12+4,{FF,{erlang,apply,2}}}, - {POS12+5,{FF,{m3,f3,2}}}, - {POS12+7,{FF,{erlang,apply,2}}}, - {POS13+1,{FF,{dm,df,1}}}, - {POS13+6,{{read,bi,0},{foo,module_info,0}}}, - {POS13+7,{{read,bi,0},{read,module_info,0}}}, - {POS13+9,{{read,bi,0},{t,foo,1}}}, - {POS14+11,{{read,bi,0},{erlang,module_info,0}}}, - {POS14+17,{{read,bi,0},{read,bi,0}}}], + {21,{{read,lc,0},{ets,tab2list,1}}}, + {POS1+1,{FF,{erlang,spawn,1}}}, + {POS1+1,{FF,{mod17,fun17,0}}}, + {POS1+2,{FF,{erlang,spawn,1}}}, + {POS1+2,{FF,{read,local,0}}}, + {POS1+3,{FF,{erlang,spawn,1}}}, + {POS1+4,{FF,{dist,func,0}}}, + {POS1+4,{FF,{erlang,spawn,1}}}, + {POS1+5,{FF,{erlang,spawn,1}}}, + {POS1+6,{FF,{erlang,spawn_link,1}}}, + {POS1+6,{FF,{mod17,fun17,0}}}, + {POS1+7,{FF,{dist,func,0}}}, + {POS1+7,{FF,{erlang,spawn_link,1}}}, + {POS1+8,{FF,{erlang,spawn_link,1}}}, + {POS2+1,{FF,{d,f,0}}}, + {POS2+1,{FF,{dist,func,2}}}, + {POS2+1,{FF,{erlang,spawn,2}}}, + {POS2+2,{FF,{dist,func,2}}}, + {POS2+2,{FF,{erlang,spawn,2}}}, + {POS2+2,{FF,{mod42,func,0}}}, + {POS2+3,{FF,{d,f,0}}}, + {POS2+3,{FF,{dist,func,2}}}, + {POS2+3,{FF,{erlang,spawn_link,2}}}, + {POS2+4,{FF,{dist,func,2}}}, + {POS2+4,{FF,{erlang,spawn_link,2}}}, + {POS2+4,{FF,{mod42,func,0}}}, + {POS3+1,{FF,{dist,func,2}}}, + {POS3+3,{FF,{dist,func,2}}}, + {POS4+1,{FF,{erlang,spawn,4}}}, + {POS4+1,{FF,{modul,function,0}}}, + {POS4+2,{FF,{erlang,spawn,4}}}, + {POS4+3,{FF,{dist,func,2}}}, + {POS4+3,{FF,{erlang,spawn,4}}}, + {POS4+3,{FF,{spm,spf,2}}}, + {POS4+4,{FF,{dist,func,2}}}, + {POS4+4,{FF,{erlang,spawn,4}}}, + {POS4+5,{FF,{dist,func,2}}}, + {POS4+5,{FF,{erlang,spawn_link,4}}}, + {POS4+5,{FF,{spm,spf,2}}}, + {POS4+6,{FF,{dist,func,2}}}, + {POS4+6,{FF,{erlang,spawn_link,4}}}, + {POS4+7,{FF,{erlang,spawn_opt,4}}}, + {POS4+7,{FF,{read,bi,0}}}, + {POS4+7,{FF,{spm,spf,2}}}, + {POS4+8,{FF,{erlang,spawn_opt,4}}}, + {POS4+8,{FF,{read,bi,0}}}, + {POS5+1,{FF,{erlang,spawn,1}}}, + {POS5+2,{FF,{erlang,spawn,1}}}, + {POS5+3,{FF,{erlang,spawn_link,1}}}, + {POS6+1,{FF,{erlang,spawn,2}}}, + {POS6+2,{FF,{erlang,spawn_link,2}}}, + {POS7+1,{FF,{erlang,spawn,4}}}, + {POS7+2,{FF,{erlang,spawn_opt,4}}}, + {POS8+1,{FF,{hej,san,1}}}, + {POS8+4,{FF,{a,b,1}}}, + {POS8+4,{FF,{erlang,apply,2}}}, + {POS8+5,{FF,{erlang,apply,2}}}, + {POS8+6,{FF,{m,f,1}}}, + {POS9+1,{FF,{read,bi,0}}}, + {POS9+2,{FF,{a,b,1}}}, + {POS9+2,{FF,{erlang,apply,2}}}, + {POS9+3,{FF,{erlang,apply,2}}}, + {POS9+4,{FF,{erlang,apply,2}}}, + {POS9+4,{FF,{erlang,not_a_function,1}}}, + {POS9+5,{FF,{mod,func,2}}}, + {POS9+6,{FF,{erlang,apply,1}}}, + {POS9+7,{FF,{erlang,apply,2}}}, + {POS9+7,{FF,{math,add3,1}}}, + {POS9+8,{FF,{q,f,1}}}, + {POS10+4,{FF,{erlang,apply,2}}}, + {POS10+5,{FF,{mod1,fun1,1}}}, + {POS11+6,{FF,{erlang,apply,2}}}, + {POS12+1,{FF,{erlang,apply,2}}}, + {POS12+4,{FF,{erlang,apply,2}}}, + {POS12+5,{FF,{m3,f3,2}}}, + {POS12+7,{FF,{erlang,apply,2}}}, + {POS13+1,{FF,{dm,df,1}}}, + {POS13+6,{{read,bi,0},{foo,module_info,0}}}, + {POS13+7,{{read,bi,0},{read,module_info,0}}}, + {POS13+9,{{read,bi,0},{t,foo,1}}}, + {POS14+11,{{read,bi,0},{erlang,module_info,0}}}, + {POS14+17,{{read,bi,0},{read,bi,0}}}], OK = case Version of - abstract_v1 -> + abstract_v1 -> [{0,{FF,{read,'$F_EXPR',178}}}, {0,{FF,{modul,'$F_EXPR',179}}}] ++ O1; - _ -> + _ -> [{16,{FF,{read,'$F_EXPR',178}}}, {17,{FF,{modul,'$F_EXPR',179}}}] ++ O1 - end, + end, %% When builtins =:= true: OKB1 = [{POS13+1,{FF,{erts_debug,apply,4}}}, {POS13+2,{FF,{erts_debug,apply,4}}}, {POS13+3,{FF,{erts_debug,apply,4}}}, - {POS1+3, {FF,{erlang,binary_to_term,1}}}, + {POS1+3, {FF,{erlang,binary_to_term,1}}}, {POS3+1, {FF,{erlang,spawn,3}}}, {POS3+2, {FF,{erlang,spawn,3}}}, {POS3+3, {FF,{erlang,spawn_link,3}}}, {POS3+4, {FF,{erlang,spawn_link,3}}}, {POS6+4, {FF,{erlang,spawn,3}}}, - {POS8+6,{FF,{erlang,apply,3}}}, - {POS8+7,{FF,{erlang,apply,3}}}, - {POS9+1,{FF,{erlang,apply,3}}}, - {POS9+5,{FF,{erlang,apply,3}}}, - {POS11+1,{FF,{erlang,apply,3}}}, - {POS11+2,{FF,{erlang,apply,3}}}, - {POS11+3,{FF,{erlang,apply,3}}}, - {POS11+4,{FF,{erlang,apply,3}}}, - {POS12+5,{FF,{erlang,apply,3}}}, - {POS12+8,{FF,{erlang,apply,3}}}, + {POS8+6,{FF,{erlang,apply,3}}}, + {POS8+7,{FF,{erlang,apply,3}}}, + {POS9+1,{FF,{erlang,apply,3}}}, + {POS9+5,{FF,{erlang,apply,3}}}, + {POS11+1,{FF,{erlang,apply,3}}}, + {POS11+2,{FF,{erlang,apply,3}}}, + {POS11+3,{FF,{erlang,apply,3}}}, + {POS11+4,{FF,{erlang,apply,3}}}, + {POS12+5,{FF,{erlang,apply,3}}}, + {POS12+8,{FF,{erlang,apply,3}}}, {POS13+5, {{read,bi,0},{erlang,length,1}}}, {POS14+3, {{read,bi,0},{erlang,length,1}}}], %% Operators (OTP-8647): OKB = case Version of abstract_v1 -> - [{POS8+3, {FF,{erlang,apply,3}}}, - {POS10+1, {FF,{erlang,apply,3}}}, - {POS10+6, {FF,{erlang,apply,3}}}]; + [{POS8+3, {FF,{erlang,apply,3}}}, + {POS10+1, {FF,{erlang,apply,3}}}, + {POS10+6, {FF,{erlang,apply,3}}}]; _ -> [{POS13+16, {{read,bi,0},{erlang,'!',2}}}, {POS13+16, {{read,bi,0},{erlang,'-',1}}}, @@ -1227,18 +1187,17 @@ read_expected(Version) -> {POS15+2, {{read,bi,0},{erlang,'*',2}}}, {POS15+8, {{read,bi,0},{erlang,'/',2}}}] end - ++ [{POS14+19, {{read,bi,0},{erlang,'+',2}}}, - {POS14+21, {{read,bi,0},{erlang,'+',2}}}, - {POS13+16, {{read,bi,0},{erlang,'==',2}}}, - {POS14+15, {{read,bi,0},{erlang,'==',2}}}, - {POS13+5, {{read,bi,0},{erlang,'>',2}}}, - {POS14+3, {{read,bi,0},{erlang,'>',2}}}] - ++ OKB1 ++ OK, + ++ [{POS14+19, {{read,bi,0},{erlang,'+',2}}}, + {POS14+21, {{read,bi,0},{erlang,'+',2}}}, + {POS13+16, {{read,bi,0},{erlang,'==',2}}}, + {POS14+15, {{read,bi,0},{erlang,'==',2}}}, + {POS13+5, {{read,bi,0},{erlang,'>',2}}}, + {POS14+3, {{read,bi,0},{erlang,'>',2}}}] + ++ OKB1 ++ OK, {U, OK, OKB}. -read2(suite) -> []; -read2(doc) -> ["Data read from the Abstract Code (cont)"]; +%% Data read from the Abstract Code (cont) read2(Conf) when is_list(Conf) -> %% Handles the spawn_opt versions added in R9 (OTP-4180). %% Expected augmentations: try/catch, cond. @@ -1248,40 +1207,40 @@ read2(Conf) when is_list(Conf) -> MFile = fname(Dir, "read2"), Beam = fname(Dir, "read2.beam"), Test = <<"-module(read2). - -compile(export_all). - - f() -> - spawn_opt({read2,f}, % POS2 - [f()]), - spawn_opt(fun() -> foo end, [link]), - spawn_opt(f(), - {read2,f}, [{min_heap_size,1000}]), - spawn_opt(f(), - fun() -> f() end, [flopp]), - spawn_opt(f(), - read2, f, [], []); - f() -> - %% Duplicated unresolved calls are ignored: - (f())(foo,bar),(f())(foo,bar). % POS1 + -compile(export_all). + + f() -> + spawn_opt({read2,f}, % POS2 + [f()]), + spawn_opt(fun() -> foo end, [link]), + spawn_opt(f(), + {read2,f}, [{min_heap_size,1000}]), + spawn_opt(f(), + fun() -> f() end, [flopp]), + spawn_opt(f(), + read2, f, [], []); + f() -> + %% Duplicated unresolved calls are ignored: + (f())(foo,bar),(f())(foo,bar). % POS1 ">>, - ?line ok = file:write_file(File, Test), - ?line {ok, read2} = compile:file(File, [debug_info,{outdir,Dir}]), + ok = file:write_file(File, Test), + {ok, read2} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, read2} = xref:add_module(s, MFile), - ?line {U0, OK0} = read2_expected(), + {ok, _} = xref:start(s), + {ok, read2} = xref:add_module(s, MFile), + {U0, OK0} = read2_expected(), U = to_external(relation_to_family(converse(from_term(U0)))), OK = to_external(relation_to_family(converse(from_term(OK0)))), - ?line {ok, U2} = xref:q(s, "(Lin) UC"), - ?line {ok, OK2} = xref:q(s, "(Lin) (E - UC)"), - ?line true = U =:= U2, - ?line true = OK =:= OK2, - ?line ok = check_state(s), - ?line xref:stop(s), - - ?line ok = file:delete(File), - ?line ok = file:delete(Beam), + {ok, U2} = xref:q(s, "(Lin) UC"), + {ok, OK2} = xref:q(s, "(Lin) (E - UC)"), + true = U =:= U2, + true = OK =:= OK2, + ok = check_state(s), + xref:stop(s), + + ok = file:delete(File), + ok = file:delete(Beam), ok. @@ -1291,36 +1250,34 @@ read2_expected() -> FF = {read2,f,0}, U = [{POS1,{FF,{'$M_EXPR','$F_EXPR',2}}}], OK = [{POS2,{FF,{erlang,spawn_opt,2}}}, - {POS2,{FF,FF}}, - {POS2+1,{FF,FF}}, - {POS2+2,{FF,{erlang,spawn_opt,2}}}, - {POS2+3,{FF,{erlang,spawn_opt,3}}}, - {POS2+3,{FF,FF}}, - {POS2+3,{FF,FF}}, - {POS2+5,{FF,{erlang,spawn_opt,3}}}, - {POS2+5,{FF,FF}}, - {POS2+6,{FF,FF}}, - {POS2+7,{FF,{erlang,spawn_opt,5}}}, - {POS2+7,{FF,FF}}, - {POS2+7,{FF,FF}}, - {POS1,{FF,FF}}], + {POS2,{FF,FF}}, + {POS2+1,{FF,FF}}, + {POS2+2,{FF,{erlang,spawn_opt,2}}}, + {POS2+3,{FF,{erlang,spawn_opt,3}}}, + {POS2+3,{FF,FF}}, + {POS2+3,{FF,FF}}, + {POS2+5,{FF,{erlang,spawn_opt,3}}}, + {POS2+5,{FF,FF}}, + {POS2+6,{FF,FF}}, + {POS2+7,{FF,{erlang,spawn_opt,5}}}, + {POS2+7,{FF,FF}}, + {POS2+7,{FF,FF}}, + {POS1,{FF,FF}}], {U, OK}. -remove(suite) -> []; -remove(doc) -> ["Remove modules, applications, releases"]; +%% Remove modules, applications, releases remove(Conf) when is_list(Conf) -> S = new(), - ?line {error, _, {no_such_module, mod}} = - xref_base:remove_module(S, mod), - ?line {error, _, {no_such_application, app}} = - xref_base:remove_application(S, app), - ?line {error, _, {no_such_release, rel}} = - xref_base:remove_release(S, rel), - ?line ok = xref_base:delete(S), + {error, _, {no_such_module, mod}} = + xref_base:remove_module(S, mod), + {error, _, {no_such_application, app}} = + xref_base:remove_application(S, app), + {error, _, {no_such_release, rel}} = + xref_base:remove_release(S, rel), + ok = xref_base:delete(S), ok. -replace(suite) -> []; -replace(doc) -> ["Replace modules, applications, releases"]; +%% Replace modules, applications, releases replace(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"rel2"), @@ -1334,105 +1291,103 @@ replace(Conf) when is_list(Conf) -> Xbeam = fname(EB1_1, "x.beam"), Ybeam = fname(EB1_1, "y.beam"), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB1_0}]), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB1_1}]), - ?line {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), - - ?line {ok, _} = start(s), - ?line {ok, false} = xref:set_default(s, verbose, false), - ?line {ok, true} = xref:set_default(s, warnings, false), - ?line {ok, rel2} = xref:add_release(s, Dir, []), - ?line {error, _, _} = xref:replace_application(s, app1, "no_data"), - ?line {error, _, {no_such_application, app12}} = - xref:replace_application(s, app12, A1_0, []), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref:replace_application(s, app1, {foo,bar}, []), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref:replace_application(s, foo, bar, [not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref:replace_application(s, foo, bar, [{builtins,not_a_value}]), - ?line {ok, app1} = - xref:replace_application(s, app1, A1_0), - ?line [{_, AppInfo}] = xref:info(s, applications, app1), - ?line {value, {release, [rel2]}} = keysearch(release, 1, AppInfo), - - ?line {error, _, {no_such_module, xx}} = - xref:replace_module(s, xx, Xbeam, []), - ?line {error, _, {invalid_options,[{builtins,true},not_an_option]}} = - xref:replace_module(s, foo, bar,[{builtins,true},not_an_option]), - ?line {error, _, {invalid_options,[{builtins,not_a_value}]}} = - xref:replace_module(s, foo, bar, [{builtins,not_a_value}]), - ?line {error, _, {invalid_filename,{foo,bar}}} = - xref:replace_module(s, x, {foo,bar}), - ?line {ok, x} = xref:replace_module(s, x, Xbeam), - ?line [{x, ModInfo}] = xref:info(s, modules, x), - ?line {value, {application, [app1]}} = - keysearch(application, 1, ModInfo), - - ?line {ok, x} = compile:file(X, [no_debug_info, {outdir,EB1_1}]), - ?line {error, _, {no_debug_info, _}} = xref:replace_module(s, x, Xbeam), - ?line {error, _, {module_mismatch, x,y}} = - xref:replace_module(s, x, Ybeam), - ?line case os:type() of - {unix, _} -> - ?line hide_file(Ybeam), - ?line {error, _, {file_error, _, _}} = - xref:replace_module(s, x, Ybeam); - _ -> - true - end, - ?line ok = xref:remove_module(s, x), - ?line {error, _, {no_debug_info, _}} = xref:add_module(s, Xbeam), + {ok, x} = compile:file(X, [debug_info, {outdir,EB1_0}]), + {ok, x} = compile:file(X, [debug_info, {outdir,EB1_1}]), + {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), + + {ok, _} = start(s), + {ok, false} = xref:set_default(s, verbose, false), + {ok, true} = xref:set_default(s, warnings, false), + {ok, rel2} = xref:add_release(s, Dir, []), + {error, _, _} = xref:replace_application(s, app1, "no_data"), + {error, _, {no_such_application, app12}} = + xref:replace_application(s, app12, A1_0, []), + {error, _, {invalid_filename,{foo,bar}}} = + xref:replace_application(s, app1, {foo,bar}, []), + {error, _, {invalid_options,[not_an_option]}} = + xref:replace_application(s, foo, bar, [not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref:replace_application(s, foo, bar, [{builtins,not_a_value}]), + {ok, app1} = + xref:replace_application(s, app1, A1_0), + [{_, AppInfo}] = xref:info(s, applications, app1), + {value, {release, [rel2]}} = keysearch(release, 1, AppInfo), + + {error, _, {no_such_module, xx}} = + xref:replace_module(s, xx, Xbeam, []), + {error, _, {invalid_options,[{builtins,true},not_an_option]}} = + xref:replace_module(s, foo, bar,[{builtins,true},not_an_option]), + {error, _, {invalid_options,[{builtins,not_a_value}]}} = + xref:replace_module(s, foo, bar, [{builtins,not_a_value}]), + {error, _, {invalid_filename,{foo,bar}}} = + xref:replace_module(s, x, {foo,bar}), + {ok, x} = xref:replace_module(s, x, Xbeam), + [{x, ModInfo}] = xref:info(s, modules, x), + {value, {application, [app1]}} = + keysearch(application, 1, ModInfo), + + {ok, x} = compile:file(X, [no_debug_info, {outdir,EB1_1}]), + {error, _, {no_debug_info, _}} = xref:replace_module(s, x, Xbeam), + {error, _, {module_mismatch, x,y}} = + xref:replace_module(s, x, Ybeam), + case os:type() of + {unix, _} -> + hide_file(Ybeam), + {error, _, {file_error, _, _}} = + xref:replace_module(s, x, Ybeam); + _ -> + true + end, + ok = xref:remove_module(s, x), + {error, _, {no_debug_info, _}} = xref:add_module(s, Xbeam), %% "app2" is ignored, the old application name is kept - ?line {ok, app1} = xref:replace_application(s, app1, A2), + {ok, app1} = xref:replace_application(s, app1, A2), - ?line xref:stop(s), - ?line ok = file:delete(fname(EB1_0, "x.beam")), - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), + xref:stop(s), + ok = file:delete(fname(EB1_0, "x.beam")), + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), ok. -update(suite) -> []; -update(doc) -> ["The update() function"]; +%% The update() function update(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"update"), Source = fname(Dir, "x.erl"), Beam = fname(Dir, "x.beam"), - ?line copy_file(fname(Dir, "x.erl.1"), Source), - ?line {ok, x} = compile:file(Source, [debug_info, {outdir,Dir}]), - - ?line {ok, _} = start(s), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), - ?line {ok, [x]} = xref:add_directory(s, Dir, [{builtins,true}]), - ?line {error, _, {invalid_options,[not_an_option]}} = - xref:update(s, [not_an_option]), - ?line {ok, []} = xref:update(s), - ?line {ok, [{erlang,atom_to_list,1}]} = xref:q(s, "XU"), - - ?line [{x, ModInfo}] = xref:info(s, modules, x), - ?line case keysearch(directory, 1, ModInfo) of - {value, {directory, Dir}} -> ok - end, + copy_file(fname(Dir, "x.erl.1"), Source), + {ok, x} = compile:file(Source, [debug_info, {outdir,Dir}]), + + {ok, _} = start(s), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, [x]} = xref:add_directory(s, Dir, [{builtins,true}]), + {error, _, {invalid_options,[not_an_option]}} = + xref:update(s, [not_an_option]), + {ok, []} = xref:update(s), + {ok, [{erlang,atom_to_list,1}]} = xref:q(s, "XU"), + + [{x, ModInfo}] = xref:info(s, modules, x), + case keysearch(directory, 1, ModInfo) of + {value, {directory, Dir}} -> ok + end, timer:sleep(2000), % make sure modification time has changed - ?line copy_file(fname(Dir, "x.erl.2"), Source), - ?line {ok, x} = compile:file(Source, [debug_info, {outdir,Dir}]), - ?line {ok, [x]} = xref:update(s, []), - ?line {ok, [{erlang,list_to_atom,1}]} = xref:q(s, "XU"), + copy_file(fname(Dir, "x.erl.2"), Source), + {ok, x} = compile:file(Source, [debug_info, {outdir,Dir}]), + {ok, [x]} = xref:update(s, []), + {ok, [{erlang,list_to_atom,1}]} = xref:q(s, "XU"), timer:sleep(2000), - ?line {ok, x} = compile:file(Source, [no_debug_info,{outdir,Dir}]), - ?line {error, _, {no_debug_info, _}} = xref:update(s), + {ok, x} = compile:file(Source, [no_debug_info,{outdir,Dir}]), + {error, _, {no_debug_info, _}} = xref:update(s), - ?line xref:stop(s), - ?line ok = file:delete(Beam), - ?line ok = file:delete(Source), + xref:stop(s), + ok = file:delete(Beam), + ok = file:delete(Source), ok. -deprecated(suite) -> []; -deprecated(doc) -> ["OTP-4695: Deprecated functions."]; +%% OTP-4695: Deprecated functions. deprecated(Conf) when is_list(Conf) -> Dir = ?copydir, File = fname(Dir, "depr.erl"), @@ -1442,79 +1397,79 @@ deprecated(Conf) when is_list(Conf) -> %% This file has been compiled to ?datadir/depr_r9c.beam %% using the R9C compiler. From R10B and onwards the linter %% checks the 'deprecated' attribute as well. -% Test = <<"-module(depr). + % Test = <<"-module(depr). -% -export([t/0,f/1,bar/2,f/2,g/3]). + % -export([t/0,f/1,bar/2,f/2,g/3]). -% -deprecated([{f,1}, % DF -% {bar,2,eventually}]). % DF_3 -% -deprecated([{f,1,next_major_release}]). % DF_2 (again) -% -deprecated([{frutt,0,next_version}]). % message... -% -deprecated([{f,2,next_major_release}, % DF_2 -% {g,3,next_version}, % DF_1 -% {ignored,10,100}]). % message... -% -deprecated([{does_not_exist,1}]). % message... + % -deprecated([{f,1}, % DF + % {bar,2,eventually}]). % DF_3 + % -deprecated([{f,1,next_major_release}]). % DF_2 (again) + % -deprecated([{frutt,0,next_version}]). % message... + % -deprecated([{f,2,next_major_release}, % DF_2 + % {g,3,next_version}, % DF_1 + % {ignored,10,100}]). % message... + % -deprecated([{does_not_exist,1}]). % message... -% -deprecated(foo). % message... + % -deprecated(foo). % message... -% t() -> -% frutt(1), -% g(1,2, 3), -% ?MODULE:f(10). + % t() -> + % frutt(1), + % g(1,2, 3), + % ?MODULE:f(10). -% f(A) -> -% ?MODULE:f(A,A). + % f(A) -> + % ?MODULE:f(A,A). -% f(X, Y) -> -% ?MODULE:g(X, Y, X). + % f(X, Y) -> + % ?MODULE:g(X, Y, X). -% g(F, G, H) -> -% ?MODULE:bar(F, {G,H}). + % g(F, G, H) -> + % ?MODULE:bar(F, {G,H}). -% bar(_, _) -> -% true. + % bar(_, _) -> + % true. -% frutt(_) -> -% frutt(). + % frutt(_) -> + % frutt(). -% frutt() -> -% true. -% ">>, + % frutt() -> + % true. + % ">>, -% ?line ok = file:write_file(File, Test), -% ?line {ok, depr_r9c} = compile:file(File, [debug_info,{outdir,Dir}]), + % ok = file:write_file(File, Test), + % {ok, depr_r9c} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, depr_r9c} = xref:add_module(s, MFile_r9c), + {ok, _} = xref:start(s), + {ok, depr_r9c} = xref:add_module(s, MFile_r9c), M9 = depr_r9c, DF_1 = usort([{{M9,f,2},{M9,g,3}}]), DF_2 = usort(DF_1++[{{M9,f,1},{M9,f,2}},{{M9,t,0},{M9,f,1}}]), DF_3 = usort(DF_2++[{{M9,g,3},{M9,bar,2}}]), DF = usort(DF_3++[{{M9,t,0},{M9,f,1}}]), - ?line {ok,DF} = xref:analyze(s, deprecated_function_calls), - ?line {ok,DF_1} = - xref:analyze(s, {deprecated_function_calls,next_version}), - ?line {ok,DF_2} = - xref:analyze(s, {deprecated_function_calls,next_major_release}), - ?line {ok,DF_3} = - xref:analyze(s, {deprecated_function_calls,eventually}), + {ok,DF} = xref:analyze(s, deprecated_function_calls), + {ok,DF_1} = + xref:analyze(s, {deprecated_function_calls,next_version}), + {ok,DF_2} = + xref:analyze(s, {deprecated_function_calls,next_major_release}), + {ok,DF_3} = + xref:analyze(s, {deprecated_function_calls,eventually}), D = to_external(range(from_term(DF))), D_1 = to_external(range(from_term(DF_1))), D_2 = to_external(range(from_term(DF_2))), D_3 = to_external(range(from_term(DF_3))), - ?line {ok,D} = xref:analyze(s, deprecated_functions), - ?line {ok,D_1} = - xref:analyze(s, {deprecated_functions,next_version}), - ?line {ok,D_2} = - xref:analyze(s, {deprecated_functions,next_major_release}), - ?line {ok,D_3} = - xref:analyze(s, {deprecated_functions,eventually}), + {ok,D} = xref:analyze(s, deprecated_functions), + {ok,D_1} = + xref:analyze(s, {deprecated_functions,next_version}), + {ok,D_2} = + xref:analyze(s, {deprecated_functions,next_major_release}), + {ok,D_3} = + xref:analyze(s, {deprecated_functions,eventually}), - ?line ok = check_state(s), - ?line xref:stop(s), + ok = check_state(s), + xref:stop(s), Test2= <<"-module(depr). @@ -1542,11 +1497,11 @@ deprecated(Conf) when is_list(Conf) -> ?MODULE:t(). ">>, - ?line ok = file:write_file(File, Test2), - ?line {ok, depr} = compile:file(File, [debug_info,{outdir,Dir}]), + ok = file:write_file(File, Test2), + {ok, depr} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, depr} = xref:add_module(s, MFile), + {ok, _} = xref:start(s), + {ok, depr} = xref:add_module(s, MFile), M = depr, DFa_1 = usort([{{M,f,2},{M,g,3}}]), @@ -1554,16 +1509,16 @@ deprecated(Conf) when is_list(Conf) -> DFa_3 = usort(DFa_2++[{{M,bar,2},{M,t,0}},{{M,g,3},{M,bar,2}}]), DFa = DFa_3, - ?line {ok,DFa} = xref:analyze(s, deprecated_function_calls), - ?line {ok,DFa_1} = - xref:analyze(s, {deprecated_function_calls,next_version}), - ?line {ok,DFa_2} = - xref:analyze(s, {deprecated_function_calls,next_major_release}), - ?line {ok,DFa_3} = - xref:analyze(s, {deprecated_function_calls,eventually}), + {ok,DFa} = xref:analyze(s, deprecated_function_calls), + {ok,DFa_1} = + xref:analyze(s, {deprecated_function_calls,next_version}), + {ok,DFa_2} = + xref:analyze(s, {deprecated_function_calls,next_major_release}), + {ok,DFa_3} = + xref:analyze(s, {deprecated_function_calls,eventually}), - ?line ok = check_state(s), - ?line xref:stop(s), + ok = check_state(s), + xref:stop(s), %% All of the module is deprecated. Test3= <<"-module(depr). @@ -1591,35 +1546,34 @@ deprecated(Conf) when is_list(Conf) -> ?MODULE:t(). ">>, - ?line ok = file:write_file(File, Test3), - ?line {ok, depr} = compile:file(File, [debug_info,{outdir,Dir}]), + ok = file:write_file(File, Test3), + {ok, depr} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, depr} = xref:add_module(s, MFile), + {ok, _} = xref:start(s), + {ok, depr} = xref:add_module(s, MFile), DFb_1 = usort([{{M,f,2},{M,g,3}}]), DFb_2 = usort(DFb_1++[{{M,f,1},{M,f,2}},{{M,t,0},{M,f,1}}]), DFb_3 = DFb_2, DFb = usort(DFb_2++[{{M,bar,2},{M,t,0}},{{M,g,3},{M,bar,2}}]), - ?line {ok,DFb} = xref:analyze(s, deprecated_function_calls), - ?line {ok,DFb_1} = - xref:analyze(s, {deprecated_function_calls,next_version}), - ?line {ok,DFb_2} = - xref:analyze(s, {deprecated_function_calls,next_major_release}), - ?line {ok,DFb_3} = - xref:analyze(s, {deprecated_function_calls,eventually}), + {ok,DFb} = xref:analyze(s, deprecated_function_calls), + {ok,DFb_1} = + xref:analyze(s, {deprecated_function_calls,next_version}), + {ok,DFb_2} = + xref:analyze(s, {deprecated_function_calls,next_major_release}), + {ok,DFb_3} = + xref:analyze(s, {deprecated_function_calls,eventually}), - ?line ok = check_state(s), - ?line xref:stop(s), + ok = check_state(s), + xref:stop(s), - ?line ok = file:delete(File), - ?line ok = file:delete(Beam), + ok = file:delete(File), + ok = file:delete(Beam), ok. -trycatch(suite) -> []; -trycatch(doc) -> ["OTP-5152: try/catch, final (?) version."]; +%% OTP-5152: try/catch, final (?) version. trycatch(Conf) when is_list(Conf) -> Dir = ?copydir, File = fname(Dir, "trycatch.erl"), @@ -1643,11 +1597,11 @@ trycatch(Conf) when is_list(Conf) -> end. ">>, - ?line ok = file:write_file(File, Test), - ?line {ok, trycatch} = compile:file(File, [debug_info,{outdir,Dir}]), + ok = file:write_file(File, Test), + {ok, trycatch} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, trycatch} = xref:add_module(s, MFile), + {ok, _} = xref:start(s), + {ok, trycatch} = xref:add_module(s, MFile), A = trycatch, {ok,[{{{A,A,0},{bar,bar,0}},[10]}, {{{A,A,0},{bar,foo,0}},[8]}, @@ -1656,18 +1610,17 @@ trycatch(Conf) when is_list(Conf) -> {{{A,A,0},{fini,shed,0}},[15]}, {{{A,A,0},{foo,bar,0}},[7]}, {{{A,A,0},{foo,foo,0}},[9]}]} = - xref:q(s, "(Lin) (E | trycatch:trycatch/0)"), + xref:q(s, "(Lin) (E | trycatch:trycatch/0)"), - ?line ok = check_state(s), - ?line xref:stop(s), + ok = check_state(s), + xref:stop(s), - ?line ok = file:delete(File), - ?line ok = file:delete(Beam), + ok = file:delete(File), + ok = file:delete(Beam), ok. -fun_mfa(suite) -> []; -fun_mfa(doc) -> ["OTP-5653: fun M:F/A."]; +%% OTP-5653: fun M:F/A. fun_mfa(Conf) when is_list(Conf) -> Dir = ?copydir, File = fname(Dir, "fun_mfa.erl"), @@ -1692,42 +1645,42 @@ fun_mfa(Conf) when is_list(Conf) -> fun t3/0(). ">>, - ?line ok = file:write_file(File, Test), + ok = file:write_file(File, Test), A = fun_mfa, - ?line {ok, A} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, A} = xref:add_module(s, MFile, {warnings,false}), - ?line {ok, [{{{A,t,0},{'$M_EXPR','$F_EXPR',0}},[7]}, - {{{A,t,0},{A,t,0}},[6]}, - {{{A,t1,0},{'$M_EXPR','$F_EXPR',0}},[11]}, - {{{A,t1,0},{A,t,0}},[10]}, - {{{A,t2,0},{A,t,0}},[14]}, - {{{A,t3,0},{fun_mfa,t3,0}},[17]}]} = - xref:q(s, "(Lin) E"), - - ?line ok = check_state(s), - ?line xref:stop(s), - - ?line ok = file:delete(File), - ?line ok = file:delete(Beam), + {ok, A} = compile:file(File, [debug_info,{outdir,Dir}]), + {ok, _} = xref:start(s), + {ok, A} = xref:add_module(s, MFile, {warnings,false}), + {ok, [{{{A,t,0},{'$M_EXPR','$F_EXPR',0}},[7]}, + {{{A,t,0},{A,t,0}},[6]}, + {{{A,t1,0},{'$M_EXPR','$F_EXPR',0}},[11]}, + {{{A,t1,0},{A,t,0}},[10]}, + {{{A,t2,0},{A,t,0}},[14]}, + {{{A,t3,0},{fun_mfa,t3,0}},[17]}]} = + xref:q(s, "(Lin) E"), + + ok = check_state(s), + xref:stop(s), + + ok = file:delete(File), + ok = file:delete(Beam), ok. %% Same as the previous test case, except that we use a BEAM file %% that was compiled by an R14 compiler to test backward compatibility. fun_mfa_r14(Conf) when is_list(Conf) -> - Dir = ?config(data_dir, Conf), + Dir = proplists:get_value(data_dir, Conf), MFile = fname(Dir, "fun_mfa_r14"), A = fun_mfa_r14, {ok, _} = xref:start(s), {ok, A} = xref:add_module(s, MFile, {warnings,false}), {ok, [{{{A,t,0},{'$M_EXPR','$F_EXPR',0}},[7]}, - {{{A,t,0},{A,t,0}},[6]}, - {{{A,t1,0},{'$M_EXPR','$F_EXPR',0}},[11]}, - {{{A,t1,0},{A,t,0}},[10]}, - {{{A,t2,0},{A,t,0}},[14]}, - {{{A,t3,0},{A,t3,0}},[17]}]} = - xref:q(s, "(Lin) E"), + {{{A,t,0},{A,t,0}},[6]}, + {{{A,t1,0},{'$M_EXPR','$F_EXPR',0}},[11]}, + {{{A,t1,0},{A,t,0}},[10]}, + {{{A,t2,0},{A,t,0}},[14]}, + {{{A,t3,0},{A,t3,0}},[17]}]} = + xref:q(s, "(Lin) E"), ok = check_state(s), xref:stop(s), @@ -1775,17 +1728,17 @@ fun_mfa_vars(Conf) when is_list(Conf) -> {ok, _} = xref:start(s), {ok, A} = xref:add_module(s, MFile, {warnings,false}), {ok, [{{{A,t,1},{'$M_EXPR','$F_EXPR',2}},[7]}, - {{{A,t,1},{'$M_EXPR',bar,2}},[6]}, - {{{A,t1,1},{'$M_EXPR','$F_EXPR',1}},[11]}, - {{{A,t1,1},{A,'$F_EXPR',1}},[10]}, - {{{A,t2,3},{'$M_EXPR','$F_EXPR',-1}},[14]}, - {{{A,t2,3},{'$M_EXPR','$F_EXPR',1}},[15]}, - {{{A,t3,1},{'$M_EXPR','$F_EXPR',3}},[19]}, - {{{A,t3,1},{fun_mfa_vars,t,-1}},[18]}, - {{{A,t4,2},{'$M_EXPR','$F_EXPR',3}},[22,23]}, - {{{A,t5,2},{'$M_EXPR','$F_EXPR',0}},[27]}, - {{{A,t5,2},{'$M_EXPR',t,-1}},[26]}]} = - xref:q(s, "(Lin) E"), + {{{A,t,1},{'$M_EXPR',bar,2}},[6]}, + {{{A,t1,1},{'$M_EXPR','$F_EXPR',1}},[11]}, + {{{A,t1,1},{A,'$F_EXPR',1}},[10]}, + {{{A,t2,3},{'$M_EXPR','$F_EXPR',-1}},[14]}, + {{{A,t2,3},{'$M_EXPR','$F_EXPR',1}},[15]}, + {{{A,t3,1},{'$M_EXPR','$F_EXPR',3}},[19]}, + {{{A,t3,1},{fun_mfa_vars,t,-1}},[18]}, + {{{A,t4,2},{'$M_EXPR','$F_EXPR',3}},[22,23]}, + {{{A,t5,2},{'$M_EXPR','$F_EXPR',0}},[27]}, + {{{A,t5,2},{'$M_EXPR',t,-1}},[26]}]} = + xref:q(s, "(Lin) E"), ok = check_state(s), xref:stop(s), @@ -1794,8 +1747,7 @@ fun_mfa_vars(Conf) when is_list(Conf) -> ok = file:delete(Beam), ok. -qlc(suite) -> []; -qlc(doc) -> ["OTP-5195: A bug fix when using qlc:q/1,2."]; +%% OTP-5195: A bug fix when using qlc:q/1,2. qlc(Conf) when is_list(Conf) -> Dir = ?copydir, File = fname(Dir, "qlc.erl"), @@ -1820,32 +1772,31 @@ qlc(Conf) when is_list(Conf) -> ok. ">>, - ?line ok = file:write_file(File, Test), + ok = file:write_file(File, Test), A = qlc, - ?line {ok, A} = compile:file(File, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, A} = xref:add_module(s, MFile, {warnings,false}), - ?line {ok, _} = xref:q(s, "(Lin) E"), % is can be loaded + {ok, A} = compile:file(File, [debug_info,{outdir,Dir}]), + {ok, _} = xref:start(s), + {ok, A} = xref:add_module(s, MFile, {warnings,false}), + {ok, _} = xref:q(s, "(Lin) E"), % is can be loaded - ?line ok = check_state(s), - ?line xref:stop(s), + ok = check_state(s), + xref:stop(s), - ?line ok = file:delete(File), - ?line ok = file:delete(Beam), + ok = file:delete(File), + ok = file:delete(Beam), ok. -analyze(suite) -> []; -analyze(doc) -> ["Simple analyses"]; +%% Simple analyses analyze(Conf) when is_list(Conf) -> S0 = new(), - ?line {{error, _, {invalid_options,[not_an_option]}}, _} = - xref_base:analyze(S0, undefined_function_calls, [not_an_option]), - ?line {{error, _, {invalid_query,{q}}}, _} = xref_base:q(S0,{q}), - ?line {{error, _, {unknown_analysis,foo}}, _} = xref_base:analyze(S0, foo), - ?line {{error, _, {unknown_constant,"foo:bar/-1"}}, _} = - xref_base:analyze(S0, {use,{foo,bar,-1}}), + {{error, _, {invalid_options,[not_an_option]}}, _} = + xref_base:analyze(S0, undefined_function_calls, [not_an_option]), + {{error, _, {invalid_query,{q}}}, _} = xref_base:q(S0,{q}), + {{error, _, {unknown_analysis,foo}}, _} = xref_base:analyze(S0, foo), + {{error, _, {unknown_constant,"foo:bar/-1"}}, _} = + xref_base:analyze(S0, {use,{foo,bar,-1}}), CopyDir = ?copydir, Dir = fname(CopyDir,"rel2"), @@ -1858,57 +1809,50 @@ analyze(Conf) when is_list(Conf) -> Xbeam = fname(EB2, "x.beam"), Ybeam = fname(EB1_1, "y.beam"), - ?line {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), - ?line {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), - - ?line {ok, rel2, S1} = xref_base:add_release(S0, Dir, [{verbose,false}]), - ?line S = set_up(S1), - - ?line {ok, _} = - analyze(undefined_function_calls, [{{x,xx,0},{x,undef,0}}], S), - ?line {ok, _} = analyze(undefined_functions, [{x,undef,0}], S), - ?line {ok, _} = analyze(locals_not_used, [{x,l,0},{x,l1,0}], S), - ?line {ok, _} = analyze(exports_not_used, [{x,xx,0},{y,t,0}], S), - - ?line {ok, _} = - analyze(deprecated_function_calls, [{{y,t,0},{x,t,0}}], S), - ?line {ok, _} = analyze({deprecated_function_calls,next_version}, [], S), - ?line {ok, _} = - analyze({deprecated_function_calls,next_major_release}, [], S), - ?line {ok, _} = analyze({deprecated_function_calls,eventually}, - [{{y,t,0},{x,t,0}}], S), - ?line {ok, _} = analyze(deprecated_functions, [{x,t,0}], S), - ?line {ok, _} = analyze({deprecated_functions,next_version}, [], S), - ?line {ok, _} = - analyze({deprecated_functions,next_major_release}, [], S), - ?line {ok, _} = analyze({deprecated_functions,eventually}, [{x,t,0}], S), - - ?line {ok, _} = analyze({call, {x,xx,0}}, [{x,undef,0}], S), - ?line {ok, _} = - analyze({call, [{x,xx,0},{x,l,0}]}, [{x,l1,0},{x,undef,0}], S), - ?line {ok, _} = analyze({use, {x,l,0}}, [{x,l1,0}], S), - ?line {ok, _} = - analyze({use, [{x,l,0},{x,l1,0}]}, [{x,l,0},{x,l1,0}], S), - - ?line {ok, _} = analyze({module_call, x}, [x], S), - ?line {ok, _} = analyze({module_call, [x,y]}, [x], S), - ?line {ok, _} = analyze({module_use, x}, [x,y], S), - ?line {ok, _} = analyze({module_use, [x,y]}, [x,y], S), - - ?line {ok, _} = analyze({application_call, app1}, [app2], S), - ?line {ok, _} = analyze({application_call, [app1,app2]}, [app2], S), - ?line {ok, _} = analyze({application_use, app2}, [app1,app2], S), - ?line {ok, _} = analyze({application_use, [app1,app2]}, [app1,app2], S), - - ?line ok = xref_base:delete(S), - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), + {ok, x} = compile:file(X, [debug_info, {outdir,EB2}]), + {ok, y} = compile:file(Y, [debug_info, {outdir,EB1_1}]), + + {ok, rel2, S1} = xref_base:add_release(S0, Dir, [{verbose,false}]), + S = set_up(S1), + + {ok, _} = analyze(undefined_function_calls, [{{x,xx,0},{x,undef,0}}], S), + {ok, _} = analyze(undefined_functions, [{x,undef,0}], S), + {ok, _} = analyze(locals_not_used, [{x,l,0},{x,l1,0}], S), + {ok, _} = analyze(exports_not_used, [{x,xx,0},{y,t,0}], S), + + {ok, _} = analyze(deprecated_function_calls, [{{y,t,0},{x,t,0}}], S), + {ok, _} = analyze({deprecated_function_calls,next_version}, [], S), + {ok, _} = analyze({deprecated_function_calls,next_major_release}, [], S), + {ok, _} = analyze({deprecated_function_calls,eventually}, + [{{y,t,0},{x,t,0}}], S), + {ok, _} = analyze(deprecated_functions, [{x,t,0}], S), + {ok, _} = analyze({deprecated_functions,next_version}, [], S), + {ok, _} = analyze({deprecated_functions,next_major_release}, [], S), + {ok, _} = analyze({deprecated_functions,eventually}, [{x,t,0}], S), + + {ok, _} = analyze({call, {x,xx,0}}, [{x,undef,0}], S), + {ok, _} = analyze({call, [{x,xx,0},{x,l,0}]}, [{x,l1,0},{x,undef,0}], S), + {ok, _} = analyze({use, {x,l,0}}, [{x,l1,0}], S), + {ok, _} = analyze({use, [{x,l,0},{x,l1,0}]}, [{x,l,0},{x,l1,0}], S), + + {ok, _} = analyze({module_call, x}, [x], S), + {ok, _} = analyze({module_call, [x,y]}, [x], S), + {ok, _} = analyze({module_use, x}, [x,y], S), + {ok, _} = analyze({module_use, [x,y]}, [x,y], S), + + {ok, _} = analyze({application_call, app1}, [app2], S), + {ok, _} = analyze({application_call, [app1,app2]}, [app2], S), + {ok, _} = analyze({application_use, app2}, [app1,app2], S), + {ok, _} = analyze({application_use, [app1,app2]}, [app1,app2], S), + + ok = xref_base:delete(S), + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), ok. -basic(suite) -> []; -basic(doc) -> ["Use of operators"]; +%% Use of operators basic(Conf) when is_list(Conf) -> - ?line S0 = new(), + S0 = new(), F1 = {m1,f1,1}, F6 = {m1,f2,6}, % X @@ -1942,8 +1886,8 @@ basic(Conf) when is_list(Conf) -> LCallAt_m1 = [{E7,12}], XCallAt_m1 = [{E1,13},{E2,17},{E4,7}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), D2 = {F2,7}, D3 = {F3,9}, @@ -1956,8 +1900,8 @@ basic(Conf) when is_list(Conf) -> LCallAt_m2 = [], XCallAt_m2 = [{E3,96},{E6,12},{UE1,77}], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), D4 = {F4,6}, D5 = {F5,97}, @@ -1969,186 +1913,185 @@ basic(Conf) when is_list(Conf) -> LCallAt_m3 = [{E5,19}], XCallAt_m3 = [{UE2,22}], Info3 = #xref_mod{name = m3, app_name = [a3]}, - ?line S3 = add_module(S2, Info3, DefAt_m3, X_m3, LCallAt_m3, XCallAt_m3, - XC_m3, LC_m3), + S3 = add_module(S2, Info3, DefAt_m3, X_m3, LCallAt_m3, XCallAt_m3, + XC_m3, LC_m3), Info4 = #xref_mod{name = m4, app_name = [a2]}, - ?line S4 = add_module(S3, Info4, [], [], [], [], [], []), + S4 = add_module(S3, Info4, [], [], [], [], [], []), AppInfo1 = #xref_app{name = a1, rel_name = [r1]}, - ?line S9 = add_application(S4, AppInfo1), + S9 = add_application(S4, AppInfo1), AppInfo2 = #xref_app{name = a2, rel_name = [r1]}, - ?line S10 = add_application(S9, AppInfo2), + S10 = add_application(S9, AppInfo2), AppInfo3 = #xref_app{name = a3, rel_name = [r2]}, - ?line S11 = add_application(S10, AppInfo3), + S11 = add_application(S10, AppInfo3), RelInfo1 = #xref_rel{name = r1}, - ?line S12 = add_release(S11, RelInfo1), + S12 = add_release(S11, RelInfo1), RelInfo2 = #xref_rel{name = r2}, - ?line S13 = add_release(S12, RelInfo2), + S13 = add_release(S12, RelInfo2), - ?line S = set_up(S13), + S = set_up(S13), - ?line {ok, _} = eval("[m1,m2] + m:f/1", unknown_constant, S), - ?line {ok, _} = eval("[m1, m2, m:f/1]", type_mismatch, S), + {ok, _} = eval("[m1,m2] + m:f/1", unknown_constant, S), + {ok, _} = eval("[m1, m2, m:f/1]", type_mismatch, S), - ?line {ok, _} = eval("[m1, m1->m2]", type_mismatch, S), - ?line {ok, _} = eval("components:f/1", unknown_constant, S), - ?line {ok, _} = eval("'of':f/1", unknown_constant, S), - ?line {ok, _} = eval("of:f/1", parse_error, S), - ?line {ok, _} = eval("components", unknown_constant, S), - ?line {ok, _} = eval("[components, of, closure]", parse_error, S), - ?line {ok, _} = eval("[components, 'of', closure]", unknown_constant, S), + {ok, _} = eval("[m1, m1->m2]", type_mismatch, S), + {ok, _} = eval("components:f/1", unknown_constant, S), + {ok, _} = eval("'of':f/1", unknown_constant, S), + {ok, _} = eval("of:f/1", parse_error, S), + {ok, _} = eval("components", unknown_constant, S), + {ok, _} = eval("[components, of, closure]", parse_error, S), + {ok, _} = eval("[components, 'of', closure]", unknown_constant, S), - ?line {ok, _} = eval("[a1->a2,m1->m2]", type_mismatch, S), - ?line {ok, _} = eval("a1->a2,m1->m2", parse_error, S), + {ok, _} = eval("[a1->a2,m1->m2]", type_mismatch, S), + {ok, _} = eval("a1->a2,m1->m2", parse_error, S), - ?line {ok, _} = eval("m1->a1", type_mismatch, S), - ?line {ok, _} = eval("[{m1,f1,1}] : App", parse_error, S), - ?line {ok, _} = eval("[{m1,f1,1}] : Fun", [F1], S), - ?line {ok, _} = eval("range X", type_error, S), - ?line {ok, _} = eval("domain X", type_error, S), - ?line {ok, _} = eval("range M", type_error, S), - ?line {ok, _} = eval("domain M", type_error, S), + {ok, _} = eval("m1->a1", type_mismatch, S), + {ok, _} = eval("[{m1,f1,1}] : App", parse_error, S), + {ok, _} = eval("[{m1,f1,1}] : Fun", [F1], S), + {ok, _} = eval("range X", type_error, S), + {ok, _} = eval("domain X", type_error, S), + {ok, _} = eval("range M", type_error, S), + {ok, _} = eval("domain M", type_error, S), % Misc. - ?line {ok, _} = eval("not_a_prefix_operator m1", parse_error, S), - ?line {ok, _} = eval(f("(Mod) ~p", [[F1,F6,F5]]), [m1,m3], S), - ?line {ok, _} = eval("(Lin) M - (Lin) m1", - [{F2,7},{F3,9},{F7,19},{F4,6},{F5,97},{UF2,0}], S), - ?line {ok, _} = eval(f("(Lin) M * (Lin) ~p", [[F1,F6]]), - [{F1,12},{F6,3}], S), - - ?line {ok, _} = eval(f("X * ~p", [[F1, F2, F3, F4, F5]]), [F3, F4], S), - ?line {ok, _} = eval("X", [F6,F3,F7,F4], S), - ?line {ok, _} = eval("X * AM", [F6,F3,F7,F4], S), - ?line {ok, _} = eval("X * a2", [F3,F7], S), - - ?line {ok, _} = eval("L * r1", [F1,F2], S), - ?line {ok, _} = eval("U", [UF1, UF2], S), - ?line {ok, _} = eval("U * AM", [UF1], S), - ?line {ok, _} = eval("U * UM", [UF2], S), - ?line {ok, _} = eval("XU * [m1, m2]", [F6,F3,F7,UF1], S), - ?line {ok, _} = eval("LU * [m3, m4]", [F5], S), - ?line {ok, _} = eval("UU", [F1,F2], S), - - ?line {ok, _} = eval("XC | m1", [E1,E2,E4], S), - ?line {ok, _} = eval(f("XC | ~p", [F1]), [E1,E4], S), - ?line {ok, _} = eval(f("(XXL) (Lin) (XC | ~p)", [F1]), - [{{D1,D3},[13]},{{D1,D4},[7]}],S), - ?line {ok, _} = eval(f("XC | (~p + ~p)", [F1, F2]), [E1,E4,E3,UE1], S), - ?line {ok, _} = eval(f("(XXL) (Lin) (XC | ~p)", [F1]), - [{{D1,D3},[13]},{{D1,D4},[7]}], S), - ?line {ok, _} = eval("LC | m3", [E5], S), - ?line {ok, _} = eval(f("LC | ~p", [F1]), [E7], S), - ?line {ok, _} = eval(f("LC | (~p + ~p)", [F1, F4]), [E7, E5], S), - ?line {ok, _} = eval("E | m1", [E1,E2,E4,E7], S), - ?line {ok, _} = eval(f("E | ~p", [F1]), [E1,E7,E4], S), - ?line {ok, _} = eval(f("E | (~p + ~p)", [F1, F2]), [E1,E7,E4,E3,UE1], S), - - ?line {ok, _} = eval("XC || m1", [E3,UE2], S), - ?line {ok, _} = eval(f("XC || ~p", [F6]), [E3], S), - ?line {ok, _} = eval(f("XC || (~p + ~p)", [F4, UF2]), [UE1,E4,E6], S), - ?line {ok, _} = eval("LC || m3", [E5], S), - ?line {ok, _} = eval(f("LC || ~p", [F1]), [], S), - ?line {ok, _} = eval(f("LC || ~p", [F6]), [E7], S), - ?line {ok, _} = eval(f("LC || (~p + ~p)", [F5, F6]), [E7,E5], S), - ?line {ok, _} = eval("E || m1", [E3,UE2,E7], S), - ?line {ok, _} = eval(f("E || ~p", [F6]), [E3,E7], S), - ?line {ok, _} = eval(f("E || (~p + ~p)", [F3,F4]), [E1,E4,E6], S), - - ?line {ok, _} = eval(f("~p + ~p", [F1,F2]), [F1,F2], S), - ?line {ok, _} = eval(f("~p * ~p", [m1,[F1,F6,F2]]), [F1,F6], S), - ?line {ok, _} = eval(f("~p * ~p", [F1,F2]), [], S), + {ok, _} = eval("not_a_prefix_operator m1", parse_error, S), + {ok, _} = eval(f("(Mod) ~p", [[F1,F6,F5]]), [m1,m3], S), + {ok, _} = eval("(Lin) M - (Lin) m1", + [{F2,7},{F3,9},{F7,19},{F4,6},{F5,97},{UF2,0}], S), + {ok, _} = eval(f("(Lin) M * (Lin) ~p", [[F1,F6]]), + [{F1,12},{F6,3}], S), + + {ok, _} = eval(f("X * ~p", [[F1, F2, F3, F4, F5]]), [F3, F4], S), + {ok, _} = eval("X", [F6,F3,F7,F4], S), + {ok, _} = eval("X * AM", [F6,F3,F7,F4], S), + {ok, _} = eval("X * a2", [F3,F7], S), + + {ok, _} = eval("L * r1", [F1,F2], S), + {ok, _} = eval("U", [UF1, UF2], S), + {ok, _} = eval("U * AM", [UF1], S), + {ok, _} = eval("U * UM", [UF2], S), + {ok, _} = eval("XU * [m1, m2]", [F6,F3,F7,UF1], S), + {ok, _} = eval("LU * [m3, m4]", [F5], S), + {ok, _} = eval("UU", [F1,F2], S), + + {ok, _} = eval("XC | m1", [E1,E2,E4], S), + {ok, _} = eval(f("XC | ~p", [F1]), [E1,E4], S), + {ok, _} = eval(f("(XXL) (Lin) (XC | ~p)", [F1]), + [{{D1,D3},[13]},{{D1,D4},[7]}],S), + {ok, _} = eval(f("XC | (~p + ~p)", [F1, F2]), [E1,E4,E3,UE1], S), + {ok, _} = eval(f("(XXL) (Lin) (XC | ~p)", [F1]), + [{{D1,D3},[13]},{{D1,D4},[7]}], S), + {ok, _} = eval("LC | m3", [E5], S), + {ok, _} = eval(f("LC | ~p", [F1]), [E7], S), + {ok, _} = eval(f("LC | (~p + ~p)", [F1, F4]), [E7, E5], S), + {ok, _} = eval("E | m1", [E1,E2,E4,E7], S), + {ok, _} = eval(f("E | ~p", [F1]), [E1,E7,E4], S), + {ok, _} = eval(f("E | (~p + ~p)", [F1, F2]), [E1,E7,E4,E3,UE1], S), + + {ok, _} = eval("XC || m1", [E3,UE2], S), + {ok, _} = eval(f("XC || ~p", [F6]), [E3], S), + {ok, _} = eval(f("XC || (~p + ~p)", [F4, UF2]), [UE1,E4,E6], S), + {ok, _} = eval("LC || m3", [E5], S), + {ok, _} = eval(f("LC || ~p", [F1]), [], S), + {ok, _} = eval(f("LC || ~p", [F6]), [E7], S), + {ok, _} = eval(f("LC || (~p + ~p)", [F5, F6]), [E7,E5], S), + {ok, _} = eval("E || m1", [E3,UE2,E7], S), + {ok, _} = eval(f("E || ~p", [F6]), [E3,E7], S), + {ok, _} = eval(f("E || (~p + ~p)", [F3,F4]), [E1,E4,E6], S), + + {ok, _} = eval(f("~p + ~p", [F1,F2]), [F1,F2], S), + {ok, _} = eval(f("~p * ~p", [m1,[F1,F6,F2]]), [F1,F6], S), + {ok, _} = eval(f("~p * ~p", [F1,F2]), [], S), %% range, domain - ?line {ok, _} = eval("range (E || m1)", [F6,UF1], S), - ?line {ok, _} = eval("domain (E || m1)", [F1,F2,F5], S), - ?line {ok, _} = eval(f("E | domain ~p", [[E1, {F2,F4}]]), - [E1,E7,E4,E3,UE1], S), + {ok, _} = eval("range (E || m1)", [F6,UF1], S), + {ok, _} = eval("domain (E || m1)", [F1,F2,F5], S), + {ok, _} = eval(f("E | domain ~p", [[E1, {F2,F4}]]), + [E1,E7,E4,E3,UE1], S), %% components, condensation, use, call - ?line {ok, _} = eval("(Lin) components E", type_error, S), - ?line {ok, _} = eval("components (Lin) E", type_error, S), - ?line {ok, _} = eval("components V", type_error, S), - ?line {ok, _} = eval("components E + components E", type_error, S), - - ?line {ok, _} = eval(f("range (closure E | ~p)", [[F1,F2]]), - [F6,F3,F7,F4,F5,UF1,UF2], S), - ?line {ok, _} = - eval(f("domain (closure E || ~p)", [[UF2,F7]]), [F1,F2,F6], S), - ?line {ok, _} = eval("components E", [], S), - ?line {ok, _} = eval("components (Mod) E", [[m1,m2,m3]], S), - ?line {ok, _} = eval("components closure (Mod) E", [[m1,m2,m3]], S), - ?line {ok, _} = eval("condensation (Mod) E", - [{[m1,m2,m3],[m17]}], S), - ?line {ok, _} = eval("condensation closure (Mod) E", - [{[m1,m2,m3],[m17]}], S), - ?line {ok, _} = eval("condensation closure closure closure (Mod) E", - [{[m1,m2,m3],[m17]}], S), - ?line {ok, _} = eval("weak condensation (Mod) E", - [{[m1,m2,m3],[m1,m2,m3]},{[m1,m2,m3],[m17]},{[m17],[m17]}], S), - ?line {ok, _} = eval("strict condensation (Mod) E", - [{[m1,m2,m3],[m17]}], S), - ?line {ok, _} = eval("range condensation (Mod) E", - [[m17]], S), - ?line {ok, _} = eval("domain condensation (Mod) E", - [[m1,m2,m3]], S), + {ok, _} = eval("(Lin) components E", type_error, S), + {ok, _} = eval("components (Lin) E", type_error, S), + {ok, _} = eval("components V", type_error, S), + {ok, _} = eval("components E + components E", type_error, S), + + {ok, _} = eval(f("range (closure E | ~p)", [[F1,F2]]), + [F6,F3,F7,F4,F5,UF1,UF2], S), + {ok, _} = + eval(f("domain (closure E || ~p)", [[UF2,F7]]), [F1,F2,F6], S), + {ok, _} = eval("components E", [], S), + {ok, _} = eval("components (Mod) E", [[m1,m2,m3]], S), + {ok, _} = eval("components closure (Mod) E", [[m1,m2,m3]], S), + {ok, _} = eval("condensation (Mod) E", + [{[m1,m2,m3],[m17]}], S), + {ok, _} = eval("condensation closure (Mod) E", + [{[m1,m2,m3],[m17]}], S), + {ok, _} = eval("condensation closure closure closure (Mod) E", + [{[m1,m2,m3],[m17]}], S), + {ok, _} = eval("weak condensation (Mod) E", + [{[m1,m2,m3],[m1,m2,m3]},{[m1,m2,m3],[m17]},{[m17],[m17]}], S), + {ok, _} = eval("strict condensation (Mod) E", + [{[m1,m2,m3],[m17]}], S), + {ok, _} = eval("range condensation (Mod) E", + [[m17]], S), + {ok, _} = eval("domain condensation (Mod) E", + [[m1,m2,m3]], S), %% |, ||, ||| - ?line {ok, _} = eval("(Lin) E || V", type_error, S), - ?line {ok, _} = eval("E ||| (Lin) V", type_error, S), - ?line {ok, _} = eval("E ||| m1", [E7], S), - ?line {ok, _} = eval("closure E ||| m1", [E7,{F1,UF1},{F6,UF1}], S), - ?line {ok, _} = eval("closure E ||| [m1,m2]", - [{F1,UF1},{F2,F7},{F1,F7},{F6,UF1},{F2,UF1},{F7,UF1},E7,E1,E2,E3], S), - ?line {ok, _} = eval("AE | a1", [{a1,a1},{a1,a2},{a1,a3}], S), + {ok, _} = eval("(Lin) E || V", type_error, S), + {ok, _} = eval("E ||| (Lin) V", type_error, S), + {ok, _} = eval("E ||| m1", [E7], S), + {ok, _} = eval("closure E ||| m1", [E7,{F1,UF1},{F6,UF1}], S), + {ok, _} = eval("closure E ||| [m1,m2]", + [{F1,UF1},{F2,F7},{F1,F7},{F6,UF1},{F2,UF1},{F7,UF1},E7,E1,E2,E3], S), + {ok, _} = eval("AE | a1", [{a1,a1},{a1,a2},{a1,a3}], S), %% path ('of') - ?line {ok, _} = eval("(Lin) {m1,m2} of E", type_error, S), - ?line {ok, _} = eval("{m1,m2} of (Lin) E", type_error, S), - ?line [m1,m2] = eval("{m1,m2} of {m1,m2}", S), - ?line {ok, _} = eval("{m1,m2} of m1", type_error, S), - ?line {ok, _} = eval("{a3,m1} of ME", type_mismatch, S), - ?line [m1,m1] = eval("{m1} of ME", S), - ?line [m1,m1] = eval("{m1} of closure closure ME", S), - ?line false = eval("{m17} of ME", S), - ?line [m2,m1,m2] = eval("{m2} : Mod of ME", S), - ?line [m1,m2,m17] = eval("{m1, m17} of ME", S), - ?line [m1,m2,m17] = eval("m1 -> m17 of ME", S), - ?line {ok, _} = eval("[m1->m17,m17->m1] of ME", type_error, S), - ?line case eval(f("~p of E", [{F1,F7,UF1}]), S) of - [F1,F6,F7,F4,F5,UF1] -> ok - end, - ?line [a2,a1,a2] = eval("{a2} of AE", S), + {ok, _} = eval("(Lin) {m1,m2} of E", type_error, S), + {ok, _} = eval("{m1,m2} of (Lin) E", type_error, S), + [m1,m2] = eval("{m1,m2} of {m1,m2}", S), + {ok, _} = eval("{m1,m2} of m1", type_error, S), + {ok, _} = eval("{a3,m1} of ME", type_mismatch, S), + [m1,m1] = eval("{m1} of ME", S), + [m1,m1] = eval("{m1} of closure closure ME", S), + false = eval("{m17} of ME", S), + [m2,m1,m2] = eval("{m2} : Mod of ME", S), + [m1,m2,m17] = eval("{m1, m17} of ME", S), + [m1,m2,m17] = eval("m1 -> m17 of ME", S), + {ok, _} = eval("[m1->m17,m17->m1] of ME", type_error, S), + case eval(f("~p of E", [{F1,F7,UF1}]), S) of + [F1,F6,F7,F4,F5,UF1] -> ok + end, + [a2,a1,a2] = eval("{a2} of AE", S), %% weak/strict - ?line {ok, _} = eval("weak {m1,m2}", [{m1,m1},{m1,m2},{m2,m2}], S), - ?line {ok, _} = eval("strict [{m1,m1},{m1,m2},{m2,m2}]", [{m1,m2}], S), - ?line {ok, _} = eval("range weak [{m1,m2}] : Mod", [m1,m2], S), - ?line {ok, _} = eval("domain strict [{m1,m1},{m1,m2},{m2,m2}]", [m1], S), + {ok, _} = eval("weak {m1,m2}", [{m1,m1},{m1,m2},{m2,m2}], S), + {ok, _} = eval("strict [{m1,m1},{m1,m2},{m2,m2}]", [{m1,m2}], S), + {ok, _} = eval("range weak [{m1,m2}] : Mod", [m1,m2], S), + {ok, _} = eval("domain strict [{m1,m1},{m1,m2},{m2,m2}]", [m1], S), %% #, number of - ?line {ok, _} = eval("# [{r1,r2}] : Rel", 1, S), - ?line {ok, _} = eval("# [{a3,a1}] : App", 1, S), - ?line {ok, _} = eval("# AE", 7, S), - ?line {ok, _} = eval("# ME", 8, S), - ?line {ok, _} = eval("# AE + # ME", 15, S), - ?line {ok, _} = eval("# AE * # ME", 56, S), - ?line {ok, _} = eval("# AE - # ME", -1, S), - ?line {ok, _} = eval("# E", 9, S), - ?line {ok, _} = eval("# V", 9, S), - ?line {ok, _} = eval("# (Lin) E", 9, S), - ?line {ok, _} = eval("# (ELin) E", 7, S), - ?line {ok, _} = eval("# closure E", type_error, S), - ?line {ok, _} = eval("# weak {m1,m2}", 3, S), - ?line {ok, _} = eval("#strict condensation (Mod) E", 1, S), - ?line {ok, _} = eval("#components closure (Mod) E", 1, S), - ?line {ok, _} = eval("# range strict condensation (Mod) E", 1, S), + {ok, _} = eval("# [{r1,r2}] : Rel", 1, S), + {ok, _} = eval("# [{a3,a1}] : App", 1, S), + {ok, _} = eval("# AE", 7, S), + {ok, _} = eval("# ME", 8, S), + {ok, _} = eval("# AE + # ME", 15, S), + {ok, _} = eval("# AE * # ME", 56, S), + {ok, _} = eval("# AE - # ME", -1, S), + {ok, _} = eval("# E", 9, S), + {ok, _} = eval("# V", 9, S), + {ok, _} = eval("# (Lin) E", 9, S), + {ok, _} = eval("# (ELin) E", 7, S), + {ok, _} = eval("# closure E", type_error, S), + {ok, _} = eval("# weak {m1,m2}", 3, S), + {ok, _} = eval("#strict condensation (Mod) E", 1, S), + {ok, _} = eval("#components closure (Mod) E", 1, S), + {ok, _} = eval("# range strict condensation (Mod) E", 1, S), ok. -md(suite) -> []; -md(doc) -> ["The xref:m() and xref:d() functions"]; +%% The xref:m() and xref:d() functions md(Conf) when is_list(Conf) -> CopyDir = ?copydir, Dir = fname(CopyDir,"md"), @@ -2157,63 +2100,61 @@ md(Conf) when is_list(Conf) -> Xbeam = fname(Dir, "x__x.beam"), Ybeam = fname(Dir, "y__y.beam"), - ?line {error, _, {invalid_filename,{foo,bar}}} = xref:m({foo,bar}), - ?line {error, _, {invalid_filename,{foo,bar}}} = xref:d({foo,bar}), + {error, _, {invalid_filename,{foo,bar}}} = xref:m({foo,bar}), + {error, _, {invalid_filename,{foo,bar}}} = xref:d({foo,bar}), - ?line {ok, x__x} = compile:file(X, [debug_info, {outdir,Dir}]), - ?line {ok, y__y} = compile:file(Y, [debug_info, {outdir,Dir}]), + {ok, x__x} = compile:file(X, [debug_info, {outdir,Dir}]), + {ok, y__y} = compile:file(Y, [debug_info, {outdir,Dir}]), - ?line {error, _, {no_such_module, foo_bar}} = xref:m(foo_bar), - ?line OldPath = code:get_path(), - ?line true = code:set_path([Dir | OldPath]), - ?line MInfo = xref:m(x__x), - ?line [{{x__x,t,1},{y__y,t,2}}] = info_tag(MInfo, undefined), - ?line [] = info_tag(MInfo, unused), - ?line [] = info_tag(MInfo, deprecated), - ?line DInfo = xref:d(Dir), - ?line [{{x__x,t,1},{y__y,t,2}}] = info_tag(DInfo, undefined), - ?line [{y__y,l,0},{y__y,l1,0}] = info_tag(DInfo, unused), - ?line [] = info_tag(MInfo, deprecated), + {error, _, {no_such_module, foo_bar}} = xref:m(foo_bar), + OldPath = code:get_path(), + true = code:set_path([Dir | OldPath]), + MInfo = xref:m(x__x), + [{{x__x,t,1},{y__y,t,2}}] = info_tag(MInfo, undefined), + [] = info_tag(MInfo, unused), + [] = info_tag(MInfo, deprecated), + DInfo = xref:d(Dir), + [{{x__x,t,1},{y__y,t,2}}] = info_tag(DInfo, undefined), + [{y__y,l,0},{y__y,l1,0}] = info_tag(DInfo, unused), + [] = info_tag(MInfo, deprecated), %% Switch from 'functions' mode to 'modules' mode. - ?line {ok, x__x} = compile:file(X, [no_debug_info, {outdir,Dir}]), - ?line {ok, y__y} = compile:file(Y, [no_debug_info, {outdir,Dir}]), - ?line MInfoMod = xref:m(x__x), - ?line [{y__y,t,2}] = info_tag(MInfoMod, undefined), - ?line [] = info_tag(MInfo, deprecated), - ?line DInfoMod = xref:d(Dir), - ?line [{y__y,t,2}] = info_tag(DInfoMod, undefined), - ?line [] = info_tag(MInfo, deprecated), - - ?line true = code:set_path(OldPath), - ?line ok = file:delete(Xbeam), - ?line ok = file:delete(Ybeam), + {ok, x__x} = compile:file(X, [no_debug_info, {outdir,Dir}]), + {ok, y__y} = compile:file(Y, [no_debug_info, {outdir,Dir}]), + MInfoMod = xref:m(x__x), + [{y__y,t,2}] = info_tag(MInfoMod, undefined), + [] = info_tag(MInfo, deprecated), + DInfoMod = xref:d(Dir), + [{y__y,t,2}] = info_tag(DInfoMod, undefined), + [] = info_tag(MInfo, deprecated), + + true = code:set_path(OldPath), + ok = file:delete(Xbeam), + ok = file:delete(Ybeam), ok. -q(suite) -> []; -q(doc) -> ["User queries"]; +%% User queries q(Conf) when is_list(Conf) -> - ?line S0 = new(), - ?line {ok, _} = eval("'foo", parse_error, S0), - ?line {ok, _} = eval("TT = E, TT = V", variable_reassigned, S0), - ?line {ok, _} = eval("TT = E, TTT", unknown_variable, S0), - ?line {ok, S} = eval("TT := E", [], S0), - ?line {ok, S1} = eval("TT * TT * TT", [], S), - ?line {ok, _S2} = xref_base:forget(S1, 'TT'), + S0 = new(), + {ok, _} = eval("'foo", parse_error, S0), + {ok, _} = eval("TT = E, TT = V", variable_reassigned, S0), + {ok, _} = eval("TT = E, TTT", unknown_variable, S0), + {ok, S} = eval("TT := E", [], S0), + {ok, S1} = eval("TT * TT * TT", [], S), + {ok, _S2} = xref_base:forget(S1, 'TT'), ok. -variables(suite) -> []; -variables(doc) -> ["Setting and getting values of query variables"]; +%% Setting and getting values of query variables variables(Conf) when is_list(Conf) -> - ?line Sa = new(), - ?line {{error, _, {invalid_options,[not_an_option]}}, _} = - xref_base:variables(Sa, [not_an_option]), - ?line {error, _, {not_user_variable,foo}} = xref_base:forget(Sa, foo), - ?line Sa1 = set_up(Sa), - ?line {error, _, {not_user_variable,foo}} = xref_base:forget(Sa1, foo), - ?line ok = xref_base:delete(Sa1), + Sa = new(), + {{error, _, {invalid_options,[not_an_option]}}, _} = + xref_base:variables(Sa, [not_an_option]), + {error, _, {not_user_variable,foo}} = xref_base:forget(Sa, foo), + Sa1 = set_up(Sa), + {error, _, {not_user_variable,foo}} = xref_base:forget(Sa1, foo), + ok = xref_base:delete(Sa1), - ?line S0 = new(), + S0 = new(), F1 = {m1,f1,1}, F2 = {m2,f1,2}, @@ -2232,8 +2173,8 @@ variables(Conf) when is_list(Conf) -> LCallAt_m1 = [], XCallAt_m1 = [{E1,13},{E3,17}], Info1 = #xref_mod{name = m1, app_name = [a1]}, - ?line S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, - XC_m1, LC_m1), + S1 = add_module(S0, Info1, DefAt_m1, X_m1, LCallAt_m1, XCallAt_m1, + XC_m1, LC_m1), D2 = {F2,7}, DefAt_m2 = [D2], @@ -2244,66 +2185,65 @@ variables(Conf) when is_list(Conf) -> LCallAt_m2 = [], XCallAt_m2 = [{E2,96}], Info2 = #xref_mod{name = m2, app_name = [a2]}, - ?line S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, - XC_m2, LC_m2), - - ?line S = set_up(S2), - - ?line eval("T1=E, T2=E*T1, T3 = T2*T2, T4=range T3, T5=T3|T4, T5", - [E1,E2,E3], S), - ?line eval("((E*E)*(E*E)) | (range ((E*E)*(E*E)))", - [E1,E2,E3], S), - ?line eval("T1=V*V,T2=T1*V,T3=V*V*V,T3", - [F1,F2,Lib], S), - ?line eval("T1=V*V, T2=V*V, T1*T2", - [F1,F2,Lib], S), - - ?line {ok, S100} = eval("T0 := E", [E1, E2, E3], S), - ?line {ok, S101} = eval("T1 := E | m1", [E1, E3], S100), - ?line {ok, S102} = eval("T2 := E | m2", [E2], S101), - ?line {{ok, [{user, ['T0', 'T1', 'T2']}]}, _} = xref_base:variables(S102), - ?line {ok, S103} = xref_base:forget(S102, 'T0'), - ?line {{ok, [{user, ['T1', 'T2']}]}, S104} = - xref_base:variables(S103, [user]), - ?line {ok, S105} = xref_base:forget(S104), - ?line {{ok, [{user, []}]}, S106} = xref_base:variables(S105), - ?line {{ok, [{predefined,_}]}, S107_0} = - xref_base:variables(S106, [predefined]), - - ?line {ok, S107_1} = - eval("TT := E, TT2 := V, TT1 := TT * TT", [E1,E2,E3], S107_0), - ?line {{ok, [{user, ['TT', 'TT1', 'TT2']}]}, _} = - xref_base:variables(S107_1), - ?line {ok, S107} = xref_base:forget(S107_1), + S2 = add_module(S1, Info2, DefAt_m2, X_m2, LCallAt_m2, XCallAt_m2, + XC_m2, LC_m2), + + S = set_up(S2), + + eval("T1=E, T2=E*T1, T3 = T2*T2, T4=range T3, T5=T3|T4, T5", + [E1,E2,E3], S), + eval("((E*E)*(E*E)) | (range ((E*E)*(E*E)))", + [E1,E2,E3], S), + eval("T1=V*V,T2=T1*V,T3=V*V*V,T3", + [F1,F2,Lib], S), + eval("T1=V*V, T2=V*V, T1*T2", + [F1,F2,Lib], S), + + {ok, S100} = eval("T0 := E", [E1, E2, E3], S), + {ok, S101} = eval("T1 := E | m1", [E1, E3], S100), + {ok, S102} = eval("T2 := E | m2", [E2], S101), + {{ok, [{user, ['T0', 'T1', 'T2']}]}, _} = xref_base:variables(S102), + {ok, S103} = xref_base:forget(S102, 'T0'), + {{ok, [{user, ['T1', 'T2']}]}, S104} = + xref_base:variables(S103, [user]), + {ok, S105} = xref_base:forget(S104), + {{ok, [{user, []}]}, S106} = xref_base:variables(S105), + {{ok, [{predefined,_}]}, S107_0} = + xref_base:variables(S106, [predefined]), + + {ok, S107_1} = + eval("TT := E, TT2 := V, TT1 := TT * TT", [E1,E2,E3], S107_0), + {{ok, [{user, ['TT', 'TT1', 'TT2']}]}, _} = + xref_base:variables(S107_1), + {ok, S107} = xref_base:forget(S107_1), CopyDir = ?copydir, - ?line Dir = fname(CopyDir,"lib_test"), + Dir = fname(CopyDir,"lib_test"), Beam = fname(Dir, "lib1.beam"), - ?line copy_file(fname(Dir, "lib1.erl"), Beam), - ?line {ok, S108} = - xref_base:set_library_path(S107, [Dir], [{verbose,false}]), - ?line {{error, _, _}, _} = xref_base:variables(S108, [{verbose,false}]), - ?line {ok, S109} = xref_base:set_library_path(S108, [], [{verbose,false}]), + copy_file(fname(Dir, "lib1.erl"), Beam), + {ok, S108} = + xref_base:set_library_path(S107, [Dir], [{verbose,false}]), + {{error, _, _}, _} = xref_base:variables(S108, [{verbose,false}]), + {ok, S109} = xref_base:set_library_path(S108, [], [{verbose,false}]), - ?line Tabs = length(ets:all()), + Tabs = length(ets:all()), - ?line {ok, S110} = eval("Eplus := closure E, TT := Eplus", - 'closure()', S109), - ?line {{ok, [{user, ['Eplus','TT']}]}, S111} = xref_base:variables(S110), - ?line {ok, S112} = xref_base:forget(S111, ['TT','Eplus']), - ?line true = Tabs =:= length(ets:all()), + {ok, S110} = eval("Eplus := closure E, TT := Eplus", + 'closure()', S109), + {{ok, [{user, ['Eplus','TT']}]}, S111} = xref_base:variables(S110), + {ok, S112} = xref_base:forget(S111, ['TT','Eplus']), + true = Tabs =:= length(ets:all()), - ?line {ok, NS0} = eval("Eplus := closure E", 'closure()', S112), - ?line {{ok, [{user, ['Eplus']}]}, NS} = xref_base:variables(NS0), - ?line ok = xref_base:delete(NS), - ?line true = Tabs =:= length(ets:all()), + {ok, NS0} = eval("Eplus := closure E", 'closure()', S112), + {{ok, [{user, ['Eplus']}]}, NS} = xref_base:variables(NS0), + ok = xref_base:delete(NS), + true = Tabs =:= length(ets:all()), - ?line ok = file:delete(Beam), + ok = file:delete(Beam), ok. -unused_locals(suite) -> []; -unused_locals(doc) -> ["OTP-5071. Too many unused functions."]; +%% OTP-5071. Too many unused functions. unused_locals(Conf) when is_list(Conf) -> Dir = ?copydir, @@ -2324,8 +2264,8 @@ unused_locals(Conf) when is_list(Conf) -> start(M, F, A) -> spawn(M, F, A). ">>, - ?line ok = file:write_file(File1, Test1), - ?line {ok, a} = compile:file(File1, [debug_info,{outdir,Dir}]), + ok = file:write_file(File1, Test1), + {ok, a} = compile:file(File1, [debug_info,{outdir,Dir}]), File2 = fname(Dir, "b.erl"), MFile2 = fname(Dir, "b"), @@ -2341,123 +2281,109 @@ unused_locals(Conf) when is_list(Conf) -> apply(a, g, [X, Y]). ">>, - ?line ok = file:write_file(File2, Test2), - ?line {ok, b} = compile:file(File2, [debug_info,{outdir,Dir}]), + ok = file:write_file(File2, Test2), + {ok, b} = compile:file(File2, [debug_info,{outdir,Dir}]), - ?line {ok, _} = xref:start(s), - ?line {ok, a} = xref:add_module(s, MFile1), - ?line {ok, b} = xref:add_module(s, MFile2), - ?line {ok, []} = xref:analyse(s, locals_not_used), - ?line ok = check_state(s), - ?line xref:stop(s), + {ok, _} = xref:start(s), + {ok, a} = xref:add_module(s, MFile1), + {ok, b} = xref:add_module(s, MFile2), + {ok, []} = xref:analyse(s, locals_not_used), + ok = check_state(s), + xref:stop(s), - ?line ok = file:delete(File1), - ?line ok = file:delete(Beam1), - ?line ok = file:delete(File2), - ?line ok = file:delete(Beam2), + ok = file:delete(File1), + ok = file:delete(Beam1), + ok = file:delete(File2), + ok = file:delete(Beam2), ok. -format_error(suite) -> []; -format_error(doc) -> ["Format error messages"]; +%% Format error messages format_error(Conf) when is_list(Conf) -> - ?line {ok, _Pid} = start(s), - ?line ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), + {ok, _Pid} = start(s), + ok = xref:set_default(s, [{verbose,false}, {warnings, false}]), %% Parse error messages. - ?line "Invalid regular expression \"add(\"" ++ _ = - fstring(xref:q(s,'"add("')), - ?line 'Invalid operator foo\n' = - fatom(xref:q(s,'foo E')), - ?line 'Invalid wildcard variable \'_Var\' (only \'_\' is allowed)\n' - = fatom(xref:q(s,"module:function/_Var")), - ?line 'Missing type of regular expression ".*"\n' - = fatom(xref:q(s,'".*"')), - ?line 'Type does not match structure of constant: \'M\' : Fun\n' - = fatom(xref:q(s,"'M' : Fun")), - ?line 'Type does not match structure of constant: ".*" : Fun\n' - = fatom(xref:q(s,'".*" : Fun')), - ?line 'Type does not match structure of constant: [m:f/1, m1:f2/3] : App\n' - = fatom(xref:q(s,"[m:f/1,m1:f2/3] : App")), - ?line 'Parse error on line 1: syntax error before: \'-\'\n' = - fatom(xref:q(s,"E + -")), - ?line "Parse error on line 1: unterminated atom starting with 'foo'\n" - = flatten(xref:format_error(xref:q(s,"'foo"))), - ?line 'Parse error at end of string: syntax error before: \n' = - fatom(xref:q(s,"E +")), - ?line 'Parse error on line 1: syntax error before: \'Lin\'\n' = - fatom(xref:q(s,"Lin")), + "Invalid regular expression \"add(\"" ++ _ = fstring(xref:q(s,'"add("')), + 'Invalid operator foo\n' = fatom(xref:q(s,'foo E')), + 'Invalid wildcard variable \'_Var\' (only \'_\' is allowed)\n' + = fatom(xref:q(s,"module:function/_Var")), + 'Missing type of regular expression ".*"\n' + = fatom(xref:q(s,'".*"')), + 'Type does not match structure of constant: \'M\' : Fun\n' + = fatom(xref:q(s,"'M' : Fun")), + 'Type does not match structure of constant: ".*" : Fun\n' + = fatom(xref:q(s,'".*" : Fun')), + 'Type does not match structure of constant: [m:f/1, m1:f2/3] : App\n' + = fatom(xref:q(s,"[m:f/1,m1:f2/3] : App")), + 'Parse error on line 1: syntax error before: \'-\'\n' + = fatom(xref:q(s,"E + -")), + "Parse error on line 1: unterminated atom starting with 'foo'\n" + = flatten(xref:format_error(xref:q(s,"'foo"))), + 'Parse error at end of string: syntax error before: \n' + = fatom(xref:q(s,"E +")), + 'Parse error on line 1: syntax error before: \'Lin\'\n' + = fatom(xref:q(s,"Lin")), %% Other messages - ?line 'Variable \'QQ\' used before set\n' = - fatom(xref:q(s,"QQ")), - ?line 'Unknown constant a\n' = - fatom(xref:q(s,"{a} of E")), + 'Variable \'QQ\' used before set\n' = fatom(xref:q(s,"QQ")), + 'Unknown constant a\n' = fatom(xref:q(s,"{a} of E")), %% Testing xref_parser:t2s/1. - ?line 'Variable assigned more than once: E := E + E\n' = - fatom(xref:q(s,"E:=E + E")), - ?line 'Variable assigned more than once: E = E + E\n' = - fatom(xref:q(s,"E=E + E")), - ?line "Operator applied to argument(s) of different or invalid type(s): " - "E + V * V\n" = - flatten(xref:format_error(xref:q(s,"E + (V * V)"))), - ?line {error,xref_compiler,{type_error,"(V + V) * E"}} = - xref:q(s,"(V + V) * E"), - ?line "Type does not match structure of constant: [m:f/3 -> g:h/17] : " - "App\n" = - flatten(xref:format_error(xref:q(s,"[{{m,f,3},{g,h,17}}] : App"))), - ?line 'Type does not match structure of constant: [m -> f, g -> h] : Fun\n' - = fatom(xref:q(s,"[{m,f},g->h] : Fun")), - ?line 'Type does not match structure of constant: {m, n, o} : Fun\n' = - fatom(xref:q(s,"{m,n,o} : Fun")), - ?line {error,xref_compiler,{type_error,"range (Lin) V"}} = - xref:q(s,"range ((Lin) V)"), - ?line {error,xref_compiler,{type_error,"condensation range E"}} = - xref:q(s,"condensation (range E)"), - ?line {error,xref_compiler,{type_error,"condensation (# E + # V)"}} = - xref:q(s,"condensation (# E + # V)"), - ?line {error,xref_compiler,{type_error,"range (# E + # E)"}} = - xref:q(s,"range (#E + #E)"), - ?line {error,xref_compiler,{type_error,"range (# E)"}} = - xref:q(s,"range #E"), % Hm... - ?line {error,xref_compiler,{type_error,"E + # E"}} = - xref:q(s,"E + #E + #E"), % Hm... - ?line {error,xref_compiler,{type_error,"V * E || V | V"}} = - xref:q(s,"V * (E || V) | V"), - ?line {error,xref_compiler,{type_error,"E || (E | V)"}} = - xref:q(s,"V * E || (E | V)"), - ?line {error,xref_compiler,{type_error,"E * \"m\" : Mod"}} = - xref:q(s,'E * "m" : Mod'), - ?line {error,xref_compiler,{type_error,"E * (\"m\":f/_ + m:\"f\"/3)"}} = - xref:q(s,'E * ("m":f/_ + m:"f"/3)'), - - ?line xref:stop(s), + 'Variable assigned more than once: E := E + E\n' = fatom(xref:q(s,"E:=E + E")), + 'Variable assigned more than once: E = E + E\n' = fatom(xref:q(s,"E=E + E")), + "Operator applied to argument(s) of different or invalid type(s): " + "E + V * V\n" = flatten(xref:format_error(xref:q(s,"E + (V * V)"))), + {error,xref_compiler,{type_error,"(V + V) * E"}} = xref:q(s,"(V + V) * E"), + "Type does not match structure of constant: [m:f/3 -> g:h/17] : " + "App\n" = flatten(xref:format_error(xref:q(s,"[{{m,f,3},{g,h,17}}] : App"))), + 'Type does not match structure of constant: [m -> f, g -> h] : Fun\n' + = fatom(xref:q(s,"[{m,f},g->h] : Fun")), + 'Type does not match structure of constant: {m, n, o} : Fun\n' = + fatom(xref:q(s,"{m,n,o} : Fun")), + {error,xref_compiler,{type_error,"range (Lin) V"}} = + xref:q(s,"range ((Lin) V)"), + {error,xref_compiler,{type_error,"condensation range E"}} = + xref:q(s,"condensation (range E)"), + {error,xref_compiler,{type_error,"condensation (# E + # V)"}} = + xref:q(s,"condensation (# E + # V)"), + {error,xref_compiler,{type_error,"range (# E + # E)"}} = + xref:q(s,"range (#E + #E)"), + {error,xref_compiler,{type_error,"range (# E)"}} = + xref:q(s,"range #E"), % Hm... + {error,xref_compiler,{type_error,"E + # E"}} = + xref:q(s,"E + #E + #E"), % Hm... + {error,xref_compiler,{type_error,"V * E || V | V"}} = + xref:q(s,"V * (E || V) | V"), + {error,xref_compiler,{type_error,"E || (E | V)"}} = + xref:q(s,"V * E || (E | V)"), + {error,xref_compiler,{type_error,"E * \"m\" : Mod"}} = + xref:q(s,'E * "m" : Mod'), + {error,xref_compiler,{type_error,"E * (\"m\":f/_ + m:\"f\"/3)"}} = + xref:q(s,'E * ("m":f/_ + m:"f"/3)'), + + xref:stop(s), ok. -otp_7423(suite) -> []; -otp_7423(doc) -> ["OTP-7423. Xref scanner bug."]; +%% OTP-7423. Xref scanner bug. otp_7423(Conf) when is_list(Conf) -> - ?line {ok, _Pid} = start(s), + {ok, _Pid} = start(s), S = "E | [compiler] : App || [{erlang, size, 1}] : Fun", - ?line {error,xref_compiler,{unknown_constant,"compiler"}} = xref:q(s,S), - ?line xref:stop(s), + {error,xref_compiler,{unknown_constant,"compiler"}} = xref:q(s,S), + xref:stop(s), ok. -otp_7831(suite) -> []; -otp_7831(doc) -> ["OTP-7831. Allow anonymous Xref processes."]; +%% OTP-7831. Allow anonymous Xref processes. otp_7831(Conf) when is_list(Conf) -> - ?line {ok, Pid1} = xref:start([]), - ?line xref:stop(Pid1), - ?line {ok, Pid2} = xref:start([{xref_mode, modules}]), - ?line xref:stop(Pid2), + {ok, Pid1} = xref:start([]), + xref:stop(Pid1), + {ok, Pid2} = xref:start([{xref_mode, modules}]), + xref:stop(Pid2), ok. -otp_10192(suite) -> []; -otp_10192(doc) -> - ["OTP-10192. Allow filenames with character codes greater than 126."]; +%% OTP-10192. Allow filenames with character codes greater than 126. otp_10192(Conf) when is_list(Conf) -> PrivDir = ?privdir, {ok, _Pid} = xref:start(s), @@ -2481,59 +2407,59 @@ fname(Dir, Basename) -> filename:join(Dir, Basename). new() -> - ?line {ok, S} = xref_base:new(), + {ok, S} = xref_base:new(), S. set_up(S) -> - ?line {ok, S1} = xref_base:set_up(S, [{verbose, false}]), + {ok, S1} = xref_base:set_up(S, [{verbose, false}]), S1. eval(Query, E, S) -> ?format("------------------------------~n", []), ?format("Evaluating ~p~n", [Query]), - ?line {Answer, NewState} = xref_base:q(S, Query, [{verbose, false}]), + {Answer, NewState} = xref_base:q(S, Query, [{verbose, false}]), {Reply, Expected} = - case Answer of - {ok, R} when is_list(E) -> - {unsetify(R), sort(E)}; - {ok, R} -> - {unsetify(R), E}; - {error, _Module, Reason} -> - {element(1, Reason), E} - end, + case Answer of + {ok, R} when is_list(E) -> + {unsetify(R), sort(E)}; + {ok, R} -> + {unsetify(R), E}; + {error, _Module, Reason} -> + {element(1, Reason), E} + end, if - Reply =:= Expected -> - ?format("As expected, got ~n~p~n", [Expected]), - {ok, NewState}; - true -> - ?format("Expected ~n~p~nbut got ~n~p~n", [Expected, Reply]), - not_ok + Reply =:= Expected -> + ?format("As expected, got ~n~p~n", [Expected]), + {ok, NewState}; + true -> + ?format("Expected ~n~p~nbut got ~n~p~n", [Expected, Reply]), + not_ok end. analyze(Query, E, S) -> ?format("------------------------------~n", []), ?format("Evaluating ~p~n", [Query]), - ?line {{ok, L}, NewState} = - xref_base:analyze(S, Query, [{verbose, false}]), + {{ok, L}, NewState} = + xref_base:analyze(S, Query, [{verbose, false}]), case {unsetify(L), sort(E)} of - {X,X} -> - ?format("As was expected, got ~n~p~n", [X]), - {ok, NewState}; - {_R,_X} -> - ?format("Expected ~n~p~nbut got ~n~p~n", [_X, _R]), - not_ok + {X,X} -> + ?format("As was expected, got ~n~p~n", [X]), + {ok, NewState}; + {_R,_X} -> + ?format("Expected ~n~p~nbut got ~n~p~n", [_X, _R]), + not_ok end. unsetify(S) -> case is_sofs_set(S) of - true -> to_external(S); - false -> S + true -> to_external(S); + false -> S end. %% Note: assumes S has been set up; the new state is not returned eval(Query, S) -> - ?line {{ok, Answer}, _NewState} = - xref_base:q(S, Query, [{verbose, false}]), + {{ok, Answer}, _NewState} = + xref_base:q(S, Query, [{verbose, false}]), unsetify(Answer). add_module(S, XMod, DefAt, X, LCallAt, XCallAt, XC, LC) -> @@ -2543,159 +2469,159 @@ add_module(S, XMod, DefAt, X, LCallAt, XCallAt, XC, LC) -> Depr = {Depr0,DBad}, Data = {DefAt, LCallAt, XCallAt, LC, XC, X, Attr, Depr}, Unres = [], - ?line {ok, _Module, _Bad, State} = - xref_base:do_add_module(S, XMod, Unres, Data), + {ok, _Module, _Bad, State} = + xref_base:do_add_module(S, XMod, Unres, Data), State. add_application(S, XApp) -> - ?line xref_base:do_add_application(S, XApp). + xref_base:do_add_application(S, XApp). add_release(S, XRel) -> - ?line xref_base:do_add_release(S, XRel). + xref_base:do_add_release(S, XRel). remove_module(S, M) -> - ?line xref_base:do_remove_module(S, M). + xref_base:do_remove_module(S, M). info_tag(Info, Tag) -> {value, {_Tag, Value}} = lists:keysearch(Tag, 1, Info), Value. make_ufile(FileName) -> - ?line ok = file:write_file(FileName, term_to_binary(foo)), - ?line hide_file(FileName). + ok = file:write_file(FileName, term_to_binary(foo)), + hide_file(FileName). make_udir(Dir) -> - ?line ok = file:make_dir(Dir), - ?line hide_file(Dir). + ok = file:make_dir(Dir), + hide_file(Dir). hide_file(FileName) -> - ?line {ok, FileInfo} = file:read_file_info(FileName), - ?line NewFileInfo = FileInfo#file_info{mode = 0}, - ?line ok = file:write_file_info(FileName, NewFileInfo). + {ok, FileInfo} = file:read_file_info(FileName), + NewFileInfo = FileInfo#file_info{mode = 0}, + ok = file:write_file_info(FileName, NewFileInfo). %% Note that S has to be set up before calling this checking function. check_state(S) -> - ?line Info = xref:info(S), + Info = xref:info(S), - ?line modules_mode_check(S, Info), + modules_mode_check(S, Info), case info(Info, mode) of - modules -> - ok; - functions -> - functions_mode_check(S, Info) + modules -> + ok; + functions -> + functions_mode_check(S, Info) end. %% The manual mentions some facts that should always hold. %% Here they are again. functions_mode_check(S, Info) -> %% F = L + X, - ?line {ok, F} = xref:q(S, "F"), - ?line {ok, F} = xref:q(S, "L + X"), + {ok, F} = xref:q(S, "F"), + {ok, F} = xref:q(S, "L + X"), %% V = X + L + B + U, - ?line {ok, V} = xref:q(S, "V"), - ?line {ok, V} = xref:q(S, "X + L + B + U"), + {ok, V} = xref:q(S, "V"), + {ok, V} = xref:q(S, "X + L + B + U"), %% X, L, B and U are disjoint. - ?line {ok, []} = - xref:q(S, "X * L + X * B + X * U + L * B + L * U + B * U"), + {ok, []} = + xref:q(S, "X * L + X * B + X * U + L * B + L * U + B * U"), %% V = UU + XU + LU, - ?line {ok, V} = xref:q(S, "UU + XU + LU"), + {ok, V} = xref:q(S, "UU + XU + LU"), %% E = LC + XC - ?line {ok, E} = xref:q(S, "E"), - ?line {ok, E} = xref:q(S, "LC + XC"), + {ok, E} = xref:q(S, "E"), + {ok, E} = xref:q(S, "LC + XC"), %% U subset of XU, - ?line {ok, []} = xref:q(S, "U - XU"), + {ok, []} = xref:q(S, "U - XU"), %% LU = range LC - ?line {ok, []} = xref:q(S, "(LU - range LC) + (range LC - LU)"), + {ok, []} = xref:q(S, "(LU - range LC) + (range LC - LU)"), %% XU = range XC - ?line {ok, []} = xref:q(S, "(XU - range XC) + (range XC - XU)"), + {ok, []} = xref:q(S, "(XU - range XC) + (range XC - XU)"), %% LU subset F - ?line {ok, []} = xref:q(S, "LU - F"), + {ok, []} = xref:q(S, "LU - F"), %% UU subset F - ?line {ok, []} = xref:q(S, "UU - F"), + {ok, []} = xref:q(S, "UU - F"), %% ME = (Mod) E - ?line {ok, ME} = xref:q(S, "ME"), - ?line {ok, ME} = xref:q(S, "(Mod) E"), + {ok, ME} = xref:q(S, "ME"), + {ok, ME} = xref:q(S, "(Mod) E"), %% AE = (App) E - ?line {ok, AE} = xref:q(S, "AE"), - ?line {ok, AE} = xref:q(S, "(App) E"), + {ok, AE} = xref:q(S, "AE"), + {ok, AE} = xref:q(S, "(App) E"), %% RE = (Rel) E - ?line {ok, RE} = xref:q(S, "RE"), - ?line {ok, RE} = xref:q(S, "(Rel) E"), + {ok, RE} = xref:q(S, "RE"), + {ok, RE} = xref:q(S, "(Rel) E"), %% (Mod) V subset of M - ?line {ok, []} = xref:q(S, "(Mod) V - M"), + {ok, []} = xref:q(S, "(Mod) V - M"), %% range UC subset of U - ?line {ok, []} = xref:q(S, "range UC - U"), + {ok, []} = xref:q(S, "range UC - U"), %% Some checks on the numbers returned by the info functions. - ?line {Resolved, Unresolved} = info(Info, no_calls), - ?line AllCalls = Resolved + Unresolved, - ?line {ok, AllCalls} = xref:q(S, "# (XLin) E + # (LLin) E"), + {Resolved, Unresolved} = info(Info, no_calls), + AllCalls = Resolved + Unresolved, + {ok, AllCalls} = xref:q(S, "# (XLin) E + # (LLin) E"), - ?line {Local, Exported} = info(Info, no_functions), - ?line LX = Local+Exported, - ?line {ok, LXs} = xref:q(S, 'Extra = _:module_info/"(0|1)" + LM, - # (F - Extra)'), - ?line true = LX =:= LXs, + {Local, Exported} = info(Info, no_functions), + LX = Local+Exported, + {ok, LXs} = xref:q(S, 'Extra = _:module_info/"(0|1)" + LM, + # (F - Extra)'), + true = LX =:= LXs, - ?line {LocalCalls, ExternalCalls, UnresCalls} = - info(Info, no_function_calls), - ?line LEU = LocalCalls + ExternalCalls + UnresCalls, - ?line {ok, LEU} = xref:q(S, "# LC + # XC"), + {LocalCalls, ExternalCalls, UnresCalls} = + info(Info, no_function_calls), + LEU = LocalCalls + ExternalCalls + UnresCalls, + {ok, LEU} = xref:q(S, "# LC + # XC"), - ?line InterFunctionCalls = info(Info, no_inter_function_calls), - ?line {ok, InterFunctionCalls} = xref:q(S, "# EE"), + InterFunctionCalls = info(Info, no_inter_function_calls), + {ok, InterFunctionCalls} = xref:q(S, "# EE"), %% And some more checks on counters... - ?line check_count(S), + check_count(S), %% ... and more - ?line {ok, []} = xref:q(S, "LM - X - U - B"), + {ok, []} = xref:q(S, "LM - X - U - B"), ok. modules_mode_check(S, Info) -> %% B subset of XU, - ?line {ok, []} = xref:q(S, "B - XU"), + {ok, []} = xref:q(S, "B - XU"), %% M = AM + LM + UM - ?line {ok, M} = xref:q(S, "M"), - ?line {ok, M} = xref:q(S, "AM + LM + UM"), + {ok, M} = xref:q(S, "M"), + {ok, M} = xref:q(S, "AM + LM + UM"), %% DF is a subset of X U B, etc. - ?line {ok, []} = xref:q(S, "DF - X - B"), - ?line {ok, []} = xref:q(S, "DF_3 - DF"), - ?line {ok, []} = xref:q(S, "DF_2 - DF_3"), - ?line {ok, []} = xref:q(S, "DF_1 - DF_2"), + {ok, []} = xref:q(S, "DF - X - B"), + {ok, []} = xref:q(S, "DF_3 - DF"), + {ok, []} = xref:q(S, "DF_2 - DF_3"), + {ok, []} = xref:q(S, "DF_1 - DF_2"), %% AM, LM and UM are disjoint. - ?line {ok, []} = xref:q(S, "AM * LM + AM * UM + LM * UM"), + {ok, []} = xref:q(S, "AM * LM + AM * UM + LM * UM"), %% (App) M subset of A - ?line {ok, []} = xref:q(S, "(App) M - A"), + {ok, []} = xref:q(S, "(App) M - A"), - ?line AM = info(Info, no_analyzed_modules), - ?line {ok, AM} = xref:q(S, "# AM"), + AM = info(Info, no_analyzed_modules), + {ok, AM} = xref:q(S, "# AM"), - ?line A = info(Info, no_applications), - ?line {ok, A} = xref:q(S, "# A"), + A = info(Info, no_applications), + {ok, A} = xref:q(S, "# A"), - ?line NoR = info(Info, no_releases), - ?line {ok, NoR} = xref:q(S, "# R"), + NoR = info(Info, no_releases), + {ok, NoR} = xref:q(S, "# R"), ok. @@ -2707,7 +2633,7 @@ check_count(S) -> {ok, M} = xref:q(S, 'AM'), {ok, _} = xref:q(S, - "Extra := _:module_info/\"(0|1)\" + LM"), + "Extra := _:module_info/\"(0|1)\" + LM"), %% info/1: {ok, NoR} = xref:q(S, '# R'), @@ -2742,7 +2668,7 @@ check_count(S) -> info_module([M | Ms], S) -> {ok, NoCalls} = per_module("T = (E | ~p : Mod), # (XLin) T + # (LLin) T", - M, S), + M, S), {ok, NoFunCalls} = per_module("# (E | ~p : Mod)", M, S), {ok, NoXCalls} = per_module("# (XC | ~p : Mod)", M, S), {ok, NoLCalls} = per_module("# (LC | ~p : Mod)", M, S), @@ -2782,40 +2708,38 @@ fstring(R) -> flatten(xref:format_error(R)). start(Server) -> - ?line case xref:start(Server) of - {error, {already_started, _Pid}} -> - ?line xref:stop(Server), - ?line xref:start(Server); - R -> R - end. + case xref:start(Server) of + {error, {already_started, _Pid}} -> + xref:stop(Server), + xref:start(Server); + R -> R + end. add_erts_code_path(KernelPath) -> VersionDirs = - filelib:is_dir( - filename:join( - [code:lib_dir(), - lists:flatten( - ["kernel-", - [X || - {kernel,_,X} <- - application_controller:which_applications()]])])), + filelib:is_dir( + filename:join( + [code:lib_dir(), + lists:flatten( + ["kernel-", + [X || + {kernel,_,X} <- + application_controller:which_applications()]])])), case VersionDirs of - true -> - case code:lib_dir(erts) of - String when is_list(String) -> - [KernelPath, fname(String,"ebin")]; - _Other1 -> - [KernelPath] - end; - false -> - % Clearcase? - PrelPath = filename:join([code:lib_dir(),"..","erts","preloaded"]), - case filelib:is_dir(PrelPath) of - true -> - [KernelPath, fname(PrelPath,"ebin")]; - false -> - [KernelPath] - end + true -> + case code:lib_dir(erts) of + String when is_list(String) -> + [KernelPath, fname(String,"ebin")]; + _Other1 -> + [KernelPath] + end; + false -> + % Clearcase? + PrelPath = filename:join([code:lib_dir(),"..","erts","preloaded"]), + case filelib:is_dir(PrelPath) of + true -> + [KernelPath, fname(PrelPath,"ebin")]; + false -> + [KernelPath] + end end. - - |