diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/horse.app.src | 24 | ||||
-rw-r--r-- | src/horse.erl | 49 | ||||
-rw-r--r-- | src/horse_autoexport.erl | 60 |
3 files changed, 133 insertions, 0 deletions
diff --git a/src/horse.app.src b/src/horse.app.src new file mode 100644 index 0000000..6ab0339 --- /dev/null +++ b/src/horse.app.src @@ -0,0 +1,24 @@ +%% Copyright (c) 2013, Loïc Hoguin <[email protected]> +%% +%% Permission to use, copy, modify, and/or distribute this software for any +%% purpose with or without fee is hereby granted, provided that the above +%% copyright notice and this permission notice appear in all copies. +%% +%% THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +%% WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +%% MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +%% ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +%% WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +%% ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +%% OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +{application, horse, [ + {description, "Integrated performance testing."}, + {vsn, "0.1.0"}, + {modules, []}, + {registered, []}, + {applications, [ + kernel, + stdlib + ]} +]}. diff --git a/src/horse.erl b/src/horse.erl new file mode 100644 index 0000000..b03a05b --- /dev/null +++ b/src/horse.erl @@ -0,0 +1,49 @@ +%% Copyright (c) 2013, Loïc Hoguin <[email protected]> +%% +%% Permission to use, copy, modify, and/or distribute this software for any +%% purpose with or without fee is hereby granted, provided that the above +%% copyright notice and this permission notice appear in all copies. +%% +%% THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +%% WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +%% MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +%% ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +%% WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +%% ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +%% OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +-module(horse). + +-export([app_perf/1]). +-export([mod_perf/1]). + +%% These might be interesting later on. +%% @todo horse_init, horse_end +%% @todo horse_init_per_test, horse_end_per_test + +app_perf(App) when is_atom(App) -> + io:format("Running horse on application ~s~n", [App]), + ok = application:load(App), + {ok, Modules} = application:get_key(App, modules), + _ = [mod_perf(M) || M <- lists:sort(Modules)], + ok. + +mod_perf(Mod) when is_atom(Mod) -> + Perfs = [F || {F, 0} <- Mod:module_info(exports), + "horse_" =:= string:substr(atom_to_list(F), 1, 6)], + _ = [fun_perf(Mod, Fun) || Fun <- Perfs], + ok. + +fun_perf(Mod, Fun) when is_atom(Mod), is_atom(Fun) -> + %% Dry run. + _ = Mod:Fun(), + %% Proper run. + Before = os:timestamp(), + _Val = Mod:Fun(), + After = os:timestamp(), + %% Results. + Time = timer:now_diff(After, Before), + "horse_" ++ Name = atom_to_list(Fun), + io:format("~s:~s in ~b.~6.10.0bs~n", + [Mod, Name, Time div 1000000, Time rem 1000000]), + ok. diff --git a/src/horse_autoexport.erl b/src/horse_autoexport.erl new file mode 100644 index 0000000..6e4a49a --- /dev/null +++ b/src/horse_autoexport.erl @@ -0,0 +1,60 @@ +%% Copyright (c) 2013, Loïc Hoguin <[email protected]> +%% +%% Permission to use, copy, modify, and/or distribute this software for any +%% purpose with or without fee is hereby granted, provided that the above +%% copyright notice and this permission notice appear in all copies. +%% +%% THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +%% WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +%% MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +%% ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +%% WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +%% ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +%% OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +-module(horse_autoexport). + +-export([parse_transform/2]). + +parse_transform([File, Module|Forms], _) -> + Exports = [F || {attribute, _, export, [{F, 0}]} <- Forms], + AutoExports = [{attribute, 0, export, [{F, 0}]} + || {function, _, F, 0, _} <- Forms, + "horse_" =:= string:substr(atom_to_list(F), 1, 6), + false =:= lists:member(F, Exports)], + replace_calls([File, Module|AutoExports ++ Forms]). + +replace_calls(Forms) -> + lists:flatten([replace_call(Form) || Form <- Forms]). + +replace_call( + {function, Fu, Name, 0, [ + {clause, Cl, [], [], [ + {call, Ca, {remote, _, {atom, _, horse}, {atom, _, repeat}}, [ + Repeat, + Expr + ]} + ]} + ]} +) when Repeat > 0 -> + GenName = list_to_atom("generated_" ++ atom_to_list(Name)), + [ + {function, Fu, Name, 0, [ + {clause, Cl, [], [], [ + {call, Ca, {atom, Ca, GenName}, [Repeat]} + ]} + ]}, + {function, Ca, GenName, 1, [ + {clause, Ca, [{integer, Ca, 0}], [], [ + {atom, Ca, ok} + ]}, + {clause, Ca, [{var, Ca, 'N'}], [], [ + Expr, + {call, Ca, {atom, Ca, GenName}, [ + {op, Ca, '-', {var, Ca, 'N'}, {integer, Ca, 1}} + ]} + ]} + ]} + ]; +replace_call(Form) -> + Form. |