[m-rev.] For review: Re-organize deep profilier tools modules.
Paul Bone
pbone at csse.unimelb.edu.au
Fri Apr 18 12:49:57 AEST 2008
For review by anyone.
Estimated Hours Taken: 1
Branches: main
Tidying up some of the deep profiler tools code. Moved data structures,
predicates and functions that are not specific to the mdprof_cgi program
from interface.m to other modules.
deep_profilier/query.m:
Moved data structures from interface.m to query.m including the cmd and
preferences data structures.
Renamed functions to replace url_compoent with string.
deep_profilier/interface.m:
Moved code from this module that doesn't relate to the mdprof_cgi
program's client-server nature to query.m and html_format.m
Conformed to predicate-renaming changes in query.m
deep_profilier/html_format.m:
Moved machine_datafile_cmd_pref_to_url function to this module.
Conform to changes in interface.m and query.m.
deep_profiler/top_procs.m:
Conform to changes in interface.m and query.m.
Index: deep_profiler/html_format.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/deep_profiler/html_format.m,v
retrieving revision 1.20
diff -u -u -r1.20 html_format.m
--- deep_profiler/html_format.m 2 Jul 2007 10:04:07 -0000 1.20
+++ deep_profiler/html_format.m 18 Apr 2008 02:41:35 -0000
@@ -17,9 +17,9 @@
:- module html_format.
:- interface.
-:- import_module interface.
:- import_module measurements.
:- import_module profile.
+:- import_module query.
:- import_module top_procs.
:- import_module bool.
@@ -2352,5 +2352,21 @@
zero_width_space = "<wbr />".
%-----------------------------------------------------------------------------%
+
+:- func machine_datafile_cmd_pref_to_url(string, string, string, cmd,
+ preferences) = string.
+
+machine_datafile_cmd_pref_to_url(Machine, ScriptName, DataFileName, Cmd,
+ Preferences) =
+ "http://" ++
+ Machine ++
+ ScriptName ++ "?" ++
+ cmd_to_string(Cmd) ++
+ string.char_to_string(query_separator_char) ++
+ preferences_to_string(Preferences) ++
+ string.char_to_string(query_separator_char) ++
+ DataFileName.
+
+%-----------------------------------------------------------------------------%
:- end_module html_format.
%-----------------------------------------------------------------------------%
Index: deep_profiler/interface.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/deep_profiler/interface.m,v
retrieving revision 1.19
diff -u -u -r1.19 interface.m
--- deep_profiler/interface.m 23 Nov 2007 07:35:51 -0000 1.19
+++ deep_profiler/interface.m 18 Apr 2008 02:41:35 -0000
@@ -33,27 +33,13 @@
% the user wants data displayed; they persist across queries unless the user
% changes them.
%
-% This module defines the types of commands and preferences. It provides
-% mechanisms for converting queries to URLs and URLs to queries, but it
-% does not expose the encoding. The encoding is compositional; each component
-% of the query (say x) has a x_to_string function to convert it to the URL form
-% and a string_to_x predicate to try to convert an URL fragment back to it.
-% The function/predicate pairs are adjacent to make it easy to update both at
-% the same time. This is essential, because we have no other mechanism to
-% ensure that the URLs we embed in the HTML pages we generate will be
-% recognized and correctly parsed by the CGI program.
-%
%-----------------------------------------------------------------------------%
:- module interface.
:- interface.
-:- import_module profile.
-
:- import_module bool.
-:- import_module char.
:- import_module io.
-:- import_module maybe.
%-----------------------------------------------------------------------------%
@@ -82,7 +68,6 @@
:- func want_prefix = string.
:- func want_file_name = string.
:- func response_file_name(string, int) = string.
-:- func contour_file_name(string) = string.
% send_term(ToFileName, Debug, Term):
%
@@ -116,224 +101,13 @@
%-----------------------------------------------------------------------------%
-:- type resp
- ---> html(string).
-
-:- type cmd_pref
- ---> cmd_pref(cmd, preferences_indication).
-
-:- type cmd
- ---> deep_cmd_quit
- ; deep_cmd_restart
- ; deep_cmd_timeout(int)
- ; deep_cmd_menu
- ; deep_cmd_root(maybe(int))
- ; deep_cmd_clique(int)
- ; deep_cmd_proc(int)
- ; deep_cmd_proc_callers(int, caller_groups, int)
- ; deep_cmd_modules
- ; deep_cmd_module(string)
- ; deep_cmd_top_procs(display_limit, cost_kind, include_descendants,
- measurement_scope)
- %
- % The following commands are for debugging.
- %
- ; deep_cmd_proc_static(int)
- ; deep_cmd_proc_dynamic(int)
- ; deep_cmd_call_site_static(int)
- ; deep_cmd_call_site_dynamic(int)
- ; deep_cmd_raw_clique(int).
-
-:- type caller_groups
- ---> group_by_call_site
- ; group_by_proc
- ; group_by_module
- ; group_by_clique.
-
-:- type cost_kind
- ---> cost_calls
- ; cost_redos
- ; cost_time
- ; cost_callseqs
- ; cost_allocs
- ; cost_words.
-
-:- type include_descendants
- ---> self
- ; self_and_desc.
-
-:- type display_limit
- ---> rank_range(int, int)
- % rank_range(M, N): display procedures with rank M to N,
- % both inclusive.
-
- ; threshold_percent(float)
- % threshold(Percent): display procedures whose cost is at least
- % Percent% of the whole program's cost.
-
- ; threshold_value(float).
- % threshold_value(Value): display procedures whose cost is at least
- % this value.
-
-:- type preferences_indication
- ---> given_pref(preferences)
- ; default_pref
- ; all_pref.
-
-:- type preferences
- ---> preferences(
- % The set of fields to display.
- pref_fields :: fields,
-
- % Whether displays should be boxed.
- pref_box :: box,
-
- % What principle governs colours.
- pref_colour :: colour_scheme,
-
- % The max number of ancestors to display.
- pref_anc :: maybe(int),
-
- % Whether pages should summarize at higher order call sites.
- pref_summarize :: summarize,
-
- % The criteria for ordering lines in pages, if the command
- % doesn't specify otherwise.
- pref_criteria :: order_criteria,
-
- % Whether contour exclusion should be applied.
- pref_contour :: contour,
-
- pref_time :: time_format,
-
- % Whether we should show modules/procs that haven't been called.
- pref_inactive :: inactive_items
- ).
-
-:- type port_fields
- ---> no_port
- ; port.
-
-:- type time_fields
- ---> no_time
- ; ticks
- ; time
- ; ticks_and_time
- ; time_and_percall
- ; ticks_and_time_and_percall.
-
-
-:- type callseqs_fields
- ---> no_callseqs
- ; callseqs
- ; callseqs_and_percall.
-
-:- type alloc_fields
- ---> no_alloc
- ; alloc
- ; alloc_and_percall.
-
-:- type memory_fields
- ---> no_memory
- ; memory(memory_units)
- ; memory_and_percall(memory_units).
-
-:- type memory_units
- ---> units_words
- ; units_bytes.
-
-:- type fields
- ---> fields(
- port_fields :: port_fields,
- time_fields :: time_fields,
- callseqs_fields :: callseqs_fields,
- alloc_fields :: alloc_fields,
- memory_fields :: memory_fields
- ).
-
-:- type box
- ---> box
- ; nobox.
-
-:- type colour_scheme
- ---> colour_column_groups
- ; colour_none.
-
-:- type summarize
- ---> summarize
- ; dont_summarize.
-
-:- type order_criteria
- ---> by_context
- ; by_name
- ; by_cost(
- cost_kind,
- include_descendants,
- measurement_scope
- ).
-
-:- type measurement_scope
- ---> per_call
- ; overall.
-
-:- type contour
- ---> apply_contour
- ; no_contour.
-
-:- type time_format
- ---> no_scale
- ; scale_by_millions
- ; scale_by_thousands.
-
-:- type inactive_status
- ---> inactive_hide
- ; inactive_show.
-
-:- type inactive_items
- ---> inactive_items(
- inactive_procs :: inactive_status,
- inactive_modules :: inactive_status
- ).
-
-%-----------------------------------------------------------------------------%
-
- % Return "yes" if it is worth displaying times for this profile.
- %
-:- func should_display_times(deep) = bool.
-
-:- func solidify_preference(deep, preferences_indication) = preferences.
-
-:- func default_preferences(deep) = preferences.
-
-:- func default_fields(deep) = fields.
-:- func all_fields = fields.
-:- func default_box = box.
-:- func default_colour_scheme = colour_scheme.
-:- func default_ancestor_limit = maybe(int).
-:- func default_summarize = summarize.
-:- func default_order_criteria = order_criteria.
-:- func default_cost_kind = cost_kind.
-:- func default_incl_desc = include_descendants.
-:- func default_scope = measurement_scope.
-:- func default_contour = contour.
-:- func default_time_format = time_format.
-:- func default_inactive_items = inactive_items.
-
-:- func query_separator_char = char.
-:- func machine_datafile_cmd_pref_to_url(string, string, string, cmd,
- preferences) = string.
-:- func url_component_to_cmd(string, cmd) = cmd.
-:- func url_component_to_maybe_cmd(string) = maybe(cmd).
-:- func url_component_to_maybe_pref(string) = maybe(preferences).
-
-%-----------------------------------------------------------------------------%
-%-----------------------------------------------------------------------------%
-
:- implementation.
:- import_module conf.
:- import_module util.
+:- import_module query.
+:- import_module char.
:- import_module int.
:- import_module list.
:- import_module require.
@@ -341,70 +115,6 @@
%-----------------------------------------------------------------------------%
- % Display times only if the profile was derived from a run that ran for
- % at least this many quanta.
- %
-:- func minimum_meaningful_quanta = int.
-
-minimum_meaningful_quanta = 10.
-
-should_display_times(Deep) =
- ( Deep ^ profile_stats ^ user_quanta > minimum_meaningful_quanta ->
- yes
- ;
- no
- ).
-
-solidify_preference(Deep, PrefInd) = Pref :-
- (
- PrefInd = given_pref(Pref)
- ;
- PrefInd = default_pref,
- Pref = default_preferences(Deep)
- ;
- PrefInd = all_pref,
- Pref = default_preferences(Deep) ^ pref_fields := all_fields
- ).
-
-default_preferences(Deep) =
- preferences(
- default_fields(Deep),
- default_box,
- default_colour_scheme,
- default_ancestor_limit,
- default_summarize,
- default_order_criteria,
- default_contour,
- default_time_format,
- default_inactive_items
- ).
-
-default_fields(Deep) = Fields :-
- ShouldDisplayTimes = should_display_times(Deep),
- (
- ShouldDisplayTimes = yes,
- Time = ticks
- ;
- ShouldDisplayTimes = no,
- Time = no_time
- ),
- Fields = fields(port, Time, callseqs, no_alloc, memory(units_words)).
-all_fields = fields(port, ticks_and_time_and_percall, callseqs_and_percall,
- alloc, memory(units_words)).
-default_box = box.
-default_colour_scheme = colour_column_groups.
-default_ancestor_limit = yes(5).
-default_summarize = dont_summarize.
-default_order_criteria = by_context.
-default_cost_kind = cost_callseqs.
-default_incl_desc = self_and_desc.
-default_scope = overall.
-default_contour = no_contour.
-default_time_format = scale_by_thousands.
-default_inactive_items = inactive_items(inactive_hide, inactive_hide).
-
-%-----------------------------------------------------------------------------%
-
to_server_pipe_name(DataFileName) =
server_dir ++ "/" ++
"mdprof_server_to" ++ filename_mangle(DataFileName).
@@ -433,9 +143,6 @@
"mdprof_response" ++ filename_mangle(DataFileName) ++
string.int_to_string(QueryNum).
-contour_file_name(DataFileName) =
- DataFileName ++ ".contour".
-
:- func server_dir = string.
server_dir = "/var/tmp".
@@ -586,567 +293,5 @@
).
%-----------------------------------------------------------------------------%
-
-:- func cmd_separator_char = char.
-:- func pref_separator_char = char.
-:- func criteria_separator_char = char.
-:- func field_separator_char = char.
-:- func limit_separator_char = char.
-
-query_separator_char = ('&').
-cmd_separator_char = ('/').
-pref_separator_char = ('/').
-criteria_separator_char = ('-').
-field_separator_char = ('-').
-limit_separator_char = ('-').
-
-machine_datafile_cmd_pref_to_url(Machine, ScriptName, DataFileName, Cmd,
- Preferences) =
- "http://" ++
- Machine ++
- ScriptName ++ "?" ++
- cmd_to_string(Cmd) ++
- string.char_to_string(query_separator_char) ++
- preferences_to_string(Preferences) ++
- string.char_to_string(query_separator_char) ++
- DataFileName.
-
-:- func cmd_to_string(cmd) = string.
-
-cmd_to_string(Cmd) = CmdStr :-
- (
- Cmd = deep_cmd_quit,
- CmdStr = "quit"
- ;
- Cmd = deep_cmd_restart,
- CmdStr = "restart"
- ;
- Cmd = deep_cmd_timeout(Minutes),
- CmdStr = string.format("timeout%c%d",
- [c(cmd_separator_char), i(Minutes)])
- ;
- Cmd = deep_cmd_menu,
- CmdStr = "menu"
- ;
- Cmd = deep_cmd_root(MaybePercent),
- (
- MaybePercent = yes(Percent),
- CmdStr = string.format("root%c%d",
- [c(cmd_separator_char), i(Percent)])
- ;
- MaybePercent = no,
- CmdStr = string.format("root%c%s",
- [c(cmd_separator_char), s("no")])
- )
- ;
- Cmd = deep_cmd_clique(CliqueNum),
- CmdStr = string.format("clique%c%d",
- [c(cmd_separator_char), i(CliqueNum)])
- ;
- Cmd = deep_cmd_proc(ProcNum),
- CmdStr = string.format("proc%c%d",
- [c(cmd_separator_char), i(ProcNum)])
- ;
- Cmd = deep_cmd_proc_callers(ProcNum, GroupCallers, BunchNum),
- GroupCallersStr = caller_groups_to_string(GroupCallers),
- CmdStr = string.format("proc_callers%c%d%c%s%c%d",
- [c(cmd_separator_char), i(ProcNum),
- c(cmd_separator_char), s(GroupCallersStr),
- c(cmd_separator_char), i(BunchNum)])
- ;
- Cmd = deep_cmd_modules,
- CmdStr = "modules"
- ;
- Cmd = deep_cmd_module(ModuleName),
- CmdStr = string.format("module%c%s",
- [c(cmd_separator_char), s(ModuleName)])
- ;
- Cmd = deep_cmd_top_procs(Limit, CostKind, InclDesc, Scope),
- LimitStr = limit_to_string(Limit),
- CostKindStr = cost_kind_to_string(CostKind),
- InclDescStr = incl_desc_to_string(InclDesc),
- ScopeStr = scope_to_string(Scope),
- CmdStr = string.format("top_procs%c%s%c%s%c%s%c%s",
- [c(cmd_separator_char), s(LimitStr),
- c(cmd_separator_char), s(CostKindStr),
- c(cmd_separator_char), s(InclDescStr),
- c(cmd_separator_char), s(ScopeStr)])
- ;
- Cmd = deep_cmd_proc_static(PSI),
- CmdStr = string.format("proc_static%c%d",
- [c(cmd_separator_char), i(PSI)])
- ;
- Cmd = deep_cmd_proc_dynamic(PDI),
- CmdStr = string.format("proc_dynamic%c%d",
- [c(cmd_separator_char), i(PDI)])
- ;
- Cmd = deep_cmd_call_site_static(CSSI),
- CmdStr = string.format("call_site_static%c%d",
- [c(cmd_separator_char), i(CSSI)])
- ;
- Cmd = deep_cmd_call_site_dynamic(CSDI),
- CmdStr = string.format("call_site_dynamic%c%d",
- [c(cmd_separator_char), i(CSDI)])
- ;
- Cmd = deep_cmd_raw_clique(CI),
- CmdStr = string.format("raw_clique%c%d",
- [c(cmd_separator_char), i(CI)])
- ).
-
-:- func preferences_to_string(preferences) = string.
-
-preferences_to_string(Pref) = PrefStr :-
- Pref = preferences(Fields, Box, Colour, MaybeAncestorLimit,
- Summarize, Order, Contour, Time, InactiveItems),
- (
- MaybeAncestorLimit = yes(AncestorLimit),
- MaybeAncestorLimitStr =
- string.format("%d", [i(AncestorLimit)])
- ;
- MaybeAncestorLimit = no,
- MaybeAncestorLimitStr = "no"
- ),
- PrefStr = string.format("%s%c%s%c%s%c%s%c%s%c%s%c%s%c%s%c%s",
- [s(fields_to_string(Fields)),
- c(pref_separator_char), s(box_to_string(Box)),
- c(pref_separator_char), s(colour_scheme_to_string(Colour)),
- c(pref_separator_char), s(MaybeAncestorLimitStr),
- c(pref_separator_char), s(summarize_to_string(Summarize)),
- c(pref_separator_char), s(order_criteria_to_string(Order)),
- c(pref_separator_char), s(contour_to_string(Contour)),
- c(pref_separator_char), s(time_format_to_string(Time)),
- c(pref_separator_char),
- s(inactive_items_to_string(InactiveItems))
- ]).
-
-url_component_to_cmd(QueryString, DefaultCmd) = Cmd :-
- MaybeCmd = url_component_to_maybe_cmd(QueryString),
- (
- MaybeCmd = yes(Cmd)
- ;
- MaybeCmd = no,
- Cmd = DefaultCmd
- ).
-
-url_component_to_maybe_cmd(QueryString) = MaybeCmd :-
- split(QueryString, pref_separator_char, Pieces),
- (
- Pieces = ["root", MaybePercentStr],
- ( MaybePercentStr = "no" ->
- MaybePercent = no
- ; string.to_int(MaybePercentStr, Percent) ->
- MaybePercent = yes(Percent)
- ;
- fail
- )
- ->
- MaybeCmd = yes(deep_cmd_root(MaybePercent))
- ;
- Pieces = ["clique", CliqueNumStr],
- string.to_int(CliqueNumStr, CliqueNum)
- ->
- MaybeCmd = yes(deep_cmd_clique(CliqueNum))
- ;
- Pieces = ["proc", PSIStr],
- string.to_int(PSIStr, PSI)
- ->
- MaybeCmd = yes(deep_cmd_proc(PSI))
- ;
- Pieces = ["proc_callers", PSIStr, GroupCallersStr, BunchNumStr],
- string.to_int(PSIStr, PSI),
- string.to_int(BunchNumStr, BunchNum),
- string_to_caller_groups(GroupCallersStr, GroupCallers)
- ->
- MaybeCmd = yes(deep_cmd_proc_callers(PSI, GroupCallers, BunchNum))
- ;
- Pieces = ["modules"]
- ->
- MaybeCmd = yes(deep_cmd_modules)
- ;
- Pieces = ["module", ModuleName]
- ->
- MaybeCmd = yes(deep_cmd_module(ModuleName))
- ;
- Pieces = ["top_procs", LimitStr, CostKindStr, InclDescStr, ScopeStr],
- string_to_limit(LimitStr, Limit),
- string_to_cost_kind(CostKindStr, CostKind),
- string_to_incl_desc(InclDescStr, InclDesc),
- string_to_scope(ScopeStr, Scope)
- ->
- MaybeCmd = yes(deep_cmd_top_procs(Limit, CostKind, InclDesc, Scope))
- ;
- Pieces = ["menu"]
- ->
- MaybeCmd = yes(deep_cmd_menu)
- ;
- Pieces = ["proc_static", PSIStr],
- string.to_int(PSIStr, PSI)
- ->
- MaybeCmd = yes(deep_cmd_proc_static(PSI))
- ;
- Pieces = ["proc_dynamic", PDIStr],
- string.to_int(PDIStr, PDI)
- ->
- MaybeCmd = yes(deep_cmd_proc_dynamic(PDI))
- ;
- Pieces = ["call_site_static", CSSIStr],
- string.to_int(CSSIStr, CSSI)
- ->
- MaybeCmd = yes(deep_cmd_call_site_static(CSSI))
- ;
- Pieces = ["call_site_dynamic", CSDIStr],
- string.to_int(CSDIStr, CSDI)
- ->
- MaybeCmd = yes(deep_cmd_call_site_dynamic(CSDI))
- ;
- Pieces = ["raw_clique", CliqueNumStr],
- string.to_int(CliqueNumStr, CliqueNum)
- ->
- MaybeCmd = yes(deep_cmd_raw_clique(CliqueNum))
- ;
- Pieces = ["timeout", TimeOutStr],
- string.to_int(TimeOutStr, TimeOut)
- ->
- MaybeCmd = yes(deep_cmd_timeout(TimeOut))
- ;
- Pieces = ["restart"]
- ->
- MaybeCmd = yes(deep_cmd_restart)
- ;
- Pieces = ["quit"]
- ->
- MaybeCmd = yes(deep_cmd_quit)
- ;
- MaybeCmd = no
- ).
-
-url_component_to_maybe_pref(QueryString) = MaybePreferences :-
- split(QueryString, pref_separator_char, Pieces),
- (
- Pieces = [FieldsStr, BoxStr, ColourStr, MaybeAncestorLimitStr,
- SummarizeStr, OrderStr, ContourStr, TimeStr,
- InactiveItemsStr],
- string_to_fields(FieldsStr, Fields),
- string_to_box(BoxStr, Box),
- string_to_colour_scheme(ColourStr, Colour),
- ( string.to_int(MaybeAncestorLimitStr, AncestorLimit) ->
- MaybeAncestorLimit = yes(AncestorLimit)
- ; MaybeAncestorLimitStr = "no" ->
- MaybeAncestorLimit = no
- ;
- fail
- ),
- string_to_summarize(SummarizeStr, Summarize),
- string_to_order_criteria(OrderStr, Order),
- string_to_contour(ContourStr, Contour),
- string_to_time_format(TimeStr, Time),
- string_to_inactive_items(InactiveItemsStr, InactiveItems)
- ->
- Preferences = preferences(Fields, Box, Colour, MaybeAncestorLimit,
- Summarize, Order, Contour, Time, InactiveItems),
- MaybePreferences = yes(Preferences)
- ;
- MaybePreferences = no
- ).
-
-%-----------------------------------------------------------------------------%
-
-:- func port_fields_to_string(port_fields) = string.
-
-port_fields_to_string(PortFields) = String :-
- string_to_port_fields(String, PortFields).
-
-:- pred string_to_port_fields(string, port_fields).
-:- mode string_to_port_fields(in, out) is semidet.
-:- mode string_to_port_fields(out, in) is det.
-
-string_to_port_fields("_", no_port).
-string_to_port_fields("p", port).
-
-:- func time_fields_to_string(time_fields) = string.
-
-time_fields_to_string(TimeFields) = String :-
- string_to_time_fields(String, TimeFields).
-
-:- pred string_to_time_fields(string, time_fields).
-:- mode string_to_time_fields(in, out) is semidet.
-:- mode string_to_time_fields(out, in) is det.
-
-string_to_time_fields("_", no_time).
-string_to_time_fields("q", ticks).
-string_to_time_fields("t", time).
-string_to_time_fields("qt", ticks_and_time).
-string_to_time_fields("tp", time_and_percall).
-string_to_time_fields("qtp", ticks_and_time_and_percall).
-
-:- func callseqs_fields_to_string(callseqs_fields) = string.
-
-callseqs_fields_to_string(AllocFields) = String :-
- string_to_callseqs_fields(String, AllocFields).
-
-:- pred string_to_callseqs_fields(string, callseqs_fields).
-:- mode string_to_callseqs_fields(in, out) is semidet.
-:- mode string_to_callseqs_fields(out, in) is det.
-
-string_to_callseqs_fields("_", no_callseqs).
-string_to_callseqs_fields("s", callseqs).
-string_to_callseqs_fields("S", callseqs_and_percall).
-
-:- func alloc_fields_to_string(alloc_fields) = string.
-
-alloc_fields_to_string(AllocFields) = String :-
- string_to_alloc_fields(String, AllocFields).
-
-:- pred string_to_alloc_fields(string, alloc_fields).
-:- mode string_to_alloc_fields(in, out) is semidet.
-:- mode string_to_alloc_fields(out, in) is det.
-
-string_to_alloc_fields("_", no_alloc).
-string_to_alloc_fields("a", alloc).
-string_to_alloc_fields("A", alloc_and_percall).
-
-:- func memory_fields_to_string(memory_fields) = string.
-
-memory_fields_to_string(MemoryFields) = String :-
- string_to_memory_fields(String, MemoryFields).
-
-:- pred string_to_memory_fields(string, memory_fields).
-:- mode string_to_memory_fields(in, out) is semidet.
-:- mode string_to_memory_fields(out, in) is det.
-
-string_to_memory_fields("_", no_memory).
-string_to_memory_fields("b", memory(units_bytes)).
-string_to_memory_fields("w", memory(units_words)).
-string_to_memory_fields("B", memory_and_percall(units_bytes)).
-string_to_memory_fields("W", memory_and_percall(units_words)).
-
-:- func fields_to_string(fields) = string.
-
-fields_to_string(fields(Port, Time, CallSeqs, Allocs, Memory)) =
- port_fields_to_string(Port) ++
- string.char_to_string(field_separator_char) ++
- time_fields_to_string(Time) ++
- string.char_to_string(field_separator_char) ++
- callseqs_fields_to_string(CallSeqs) ++
- string.char_to_string(field_separator_char) ++
- alloc_fields_to_string(Allocs) ++
- string.char_to_string(field_separator_char) ++
- memory_fields_to_string(Memory).
-
-:- pred string_to_fields(string::in, fields::out) is semidet.
-
-string_to_fields(FieldsStr, Fields) :-
- (
- split(FieldsStr, field_separator_char, Pieces),
- Pieces = [PortStr, TimeStr, CallSeqsStr, AllocStr, MemoryStr],
- string_to_port_fields(PortStr, Port),
- string_to_time_fields(TimeStr, Time),
- string_to_callseqs_fields(CallSeqsStr, CallSeqs),
- string_to_alloc_fields(AllocStr, Alloc),
- string_to_memory_fields(MemoryStr, Memory)
- ->
- Fields = fields(Port, Time, CallSeqs, Alloc, Memory)
- ;
- fail
- ).
-
-:- func caller_groups_to_string(caller_groups) = string.
-
-caller_groups_to_string(CallerGroups) = String :-
- string_to_caller_groups(String, CallerGroups).
-
-:- pred string_to_caller_groups(string, caller_groups).
-:- mode string_to_caller_groups(in, out) is semidet.
-:- mode string_to_caller_groups(out, in) is det.
-
-string_to_caller_groups("cs", group_by_call_site).
-string_to_caller_groups("pr", group_by_proc).
-string_to_caller_groups("mo", group_by_module).
-string_to_caller_groups("cl", group_by_clique).
-
-:- func cost_kind_to_string(cost_kind) = string.
-
-cost_kind_to_string(CostKind) = String :-
- string_to_cost_kind(String, CostKind).
-
-:- pred string_to_cost_kind(string, cost_kind).
-:- mode string_to_cost_kind(in, out) is semidet.
-:- mode string_to_cost_kind(out, in) is det.
-
-string_to_cost_kind("calls", cost_calls).
-string_to_cost_kind("redos", cost_redos).
-string_to_cost_kind("time", cost_time).
-string_to_cost_kind("callseqs", cost_callseqs).
-string_to_cost_kind("allocs", cost_allocs).
-string_to_cost_kind("words", cost_words).
-
-:- func incl_desc_to_string(include_descendants) = string.
-
-incl_desc_to_string(InclDesc) = String :-
- string_to_incl_desc(String, InclDesc).
-
-:- pred string_to_incl_desc(string, include_descendants).
-:- mode string_to_incl_desc(in, out) is semidet.
-:- mode string_to_incl_desc(out, in) is det.
-
-string_to_incl_desc("self", self).
-string_to_incl_desc("both", self_and_desc).
-
-:- func limit_to_string(display_limit) = string.
-
-limit_to_string(rank_range(Lo, Hi)) =
- string.format("%d%c%d", [i(Lo), c(limit_separator_char), i(Hi)]).
-limit_to_string(threshold_percent(Threshold)) =
- string.format("p%g", [f(Threshold)]).
-limit_to_string(threshold_value(Value)) =
- string.format("v%g", [f(Value)]).
-
-:- pred string_to_limit(string::in, display_limit::out) is semidet.
-
-string_to_limit(LimitStr, Limit) :-
- (
- split(LimitStr, limit_separator_char, Pieces),
- Pieces = [FirstStr, LastStr],
- string.to_int(FirstStr, First),
- string.to_int(LastStr, Last)
- ->
- Limit = rank_range(First, Last)
- ;
- string.append("p", PercentStr, LimitStr),
- string.to_float(PercentStr, Threshold)
- ->
- Limit = threshold_percent(Threshold)
- ;
- string.append("v", ValueStr, LimitStr),
- string.to_float(ValueStr, Value)
- ->
- Limit = threshold_value(Value)
- ;
- fail
- ).
-
-:- func summarize_to_string(summarize) = string.
-
-summarize_to_string(summarize) = "sum".
-summarize_to_string(dont_summarize) = "nosum".
-
-:- pred string_to_summarize(string::in, summarize::out) is semidet.
-
-string_to_summarize("sum", summarize).
-string_to_summarize("nosum", dont_summarize).
-
-:- func order_criteria_to_string(order_criteria) = string.
-
-order_criteria_to_string(by_context) = "context".
-order_criteria_to_string(by_name) = "name".
-order_criteria_to_string(by_cost(CostKind, InclDesc, Scope)) =
- "cost" ++
- string.char_to_string(criteria_separator_char) ++
- cost_kind_to_string(CostKind) ++
- string.char_to_string(criteria_separator_char) ++
- incl_desc_to_string(InclDesc) ++
- string.char_to_string(criteria_separator_char) ++
- scope_to_string(Scope).
-
-:- pred string_to_order_criteria(string::in, order_criteria::out) is semidet.
-
-string_to_order_criteria(CriteriaStr, Criteria) :-
- (
- CriteriaStr = "context"
- ->
- Criteria = by_context
- ;
- CriteriaStr = "name"
- ->
- Criteria = by_name
- ;
- split(CriteriaStr, criteria_separator_char, Pieces),
- Pieces = ["cost", CostKindStr, InclDescStr, ScopeStr],
- string_to_cost_kind(CostKindStr, CostKind),
- string_to_incl_desc(InclDescStr, InclDesc),
- string_to_scope(ScopeStr, Scope)
- ->
- Criteria = by_cost(CostKind, InclDesc, Scope)
- ;
- fail
- ).
-
-:- func scope_to_string(measurement_scope) = string.
-
-scope_to_string(Scope) = String :-
- string_to_scope(String, Scope).
-
-:- pred string_to_scope(string, measurement_scope).
-:- mode string_to_scope(in, out) is semidet.
-:- mode string_to_scope(out, in) is det.
-
-string_to_scope("pc", per_call).
-string_to_scope("oa", overall).
-
-:- func contour_to_string(contour) = string.
-
-contour_to_string(Contour) = String :-
- string_to_contour(String, Contour).
-
-:- pred string_to_contour(string, contour).
-:- mode string_to_contour(in, out) is semidet.
-:- mode string_to_contour(out, in) is det.
-
-string_to_contour("ac", apply_contour).
-string_to_contour("nc", no_contour).
-
-:- func time_format_to_string(time_format) = string.
-
-time_format_to_string(no_scale) = "no".
-time_format_to_string(scale_by_millions) = "mi".
-time_format_to_string(scale_by_thousands) = "th".
-
-:- pred string_to_time_format(string, time_format).
-:- mode string_to_time_format(in, out) is semidet.
-:- mode string_to_time_format(out, in) is det.
-
-string_to_time_format("no", no_scale).
-string_to_time_format("mi", scale_by_millions).
-string_to_time_format("th", scale_by_thousands).
-
-:- func inactive_items_to_string(inactive_items) = string.
-
-inactive_items_to_string(Items) = String :-
- string_to_inactive_items(String, Items).
-
-:- pred string_to_inactive_items(string, inactive_items).
-:- mode string_to_inactive_items(in, out) is semidet.
-:- mode string_to_inactive_items(out, in) is det.
-
-string_to_inactive_items("hh", inactive_items(inactive_hide, inactive_hide)).
-string_to_inactive_items("sh", inactive_items(inactive_show, inactive_hide)).
-string_to_inactive_items("hs", inactive_items(inactive_hide, inactive_show)).
-string_to_inactive_items("ss", inactive_items(inactive_show, inactive_show)).
-
-:- func colour_scheme_to_string(colour_scheme) = string.
-
-colour_scheme_to_string(Scheme) = String :-
- string_to_colour_scheme(String, Scheme).
-
-:- pred string_to_colour_scheme(string, colour_scheme).
-:- mode string_to_colour_scheme(in, out) is semidet.
-:- mode string_to_colour_scheme(out, in) is det.
-
-string_to_colour_scheme("cols", colour_column_groups).
-string_to_colour_scheme("none", colour_none).
-
-:- func box_to_string(box) = string.
-
-box_to_string(Box) = String :-
- string_to_box(String, Box).
-
-:- pred string_to_box(string, box).
-:- mode string_to_box(in, out) is semidet.
-:- mode string_to_box(out, in) is det.
-
-string_to_box("box", box).
-string_to_box("nobox", nobox).
-
-%-----------------------------------------------------------------------------%
:- end_module interface.
%-----------------------------------------------------------------------------%
Index: deep_profiler/mdprof_cgi.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/deep_profiler/mdprof_cgi.m,v
retrieving revision 1.21
diff -u -u -r1.21 mdprof_cgi.m
--- deep_profiler/mdprof_cgi.m 17 Feb 2008 06:48:38 -0000 1.21
+++ deep_profiler/mdprof_cgi.m 18 Apr 2008 02:41:35 -0000
@@ -71,10 +71,10 @@
),
split(QueryString0, query_separator_char, Pieces),
( Pieces = [CmdStr, PrefStr, FileName] ->
- Cmd = url_component_to_cmd(CmdStr, deep_cmd_menu),
+ Cmd = string_to_cmd(CmdStr, deep_cmd_menu),
process_query(Cmd, yes(PrefStr), FileName, Options, !IO)
; Pieces = [CmdStr, FileName] ->
- Cmd = url_component_to_cmd(CmdStr, deep_cmd_menu),
+ Cmd = string_to_cmd(CmdStr, deep_cmd_menu),
process_query(Cmd, no, FileName, Options, !IO)
; Pieces = [FileName] ->
process_query(deep_cmd_menu, no, FileName, Options, !IO)
@@ -197,7 +197,7 @@
process_query(Cmd, MaybePrefStr, DataFileName0, Options0, !IO) :-
(
MaybePrefStr = yes(PrefStr),
- MaybePref = url_component_to_maybe_pref(PrefStr)
+ MaybePref = string_to_maybe_pref(PrefStr)
;
MaybePrefStr = no,
MaybePref = no
Index: deep_profiler/query.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/deep_profiler/query.m,v
retrieving revision 1.18
diff -u -u -r1.18 query.m
--- deep_profiler/query.m 23 Nov 2007 07:35:52 -0000 1.18
+++ deep_profiler/query.m 18 Apr 2008 02:41:35 -0000
@@ -11,15 +11,28 @@
%
% This module contains the top level predicates for servicing individual
% queries.
+%
+% This module defines the types of commands and preferences. It provides
+% mechanisms for converting queries to strings and strings to queries, but
+% it does not expose the encoding. The encoding is compositional; each
+% component of the query (say x) has a x_to_string function to convert it to
+% a string and a string_to_x predicate to try to convert a string fragment
+% back to it. The function/predicate pairs are adjacent to make it easy to
+% update both at the same time. This is essential, because we have no other
+% mechanism to ensure that the URLs embeded in the HTML pages generated by
+% the mdprof_cgi tool will be recognized and correctly parsed by mdprof_cgi.
+%
%-----------------------------------------------------------------------------%
:- module query.
:- interface.
:- import_module profile.
-:- import_module interface.
+:- import_module bool.
+:- import_module char.
:- import_module io.
+:- import_module maybe.
%-----------------------------------------------------------------------------%
@@ -27,6 +40,219 @@
io::di, io::uo) is cc_multi.
%-----------------------------------------------------------------------------%
+
+:- type resp
+ ---> html(string).
+
+:- type cmd_pref
+ ---> cmd_pref(cmd, preferences_indication).
+
+:- type cmd
+ ---> deep_cmd_quit
+ ; deep_cmd_restart
+ ; deep_cmd_timeout(int)
+ ; deep_cmd_menu
+ ; deep_cmd_root(maybe(int))
+ ; deep_cmd_clique(int)
+ ; deep_cmd_proc(int)
+ ; deep_cmd_proc_callers(int, caller_groups, int)
+ ; deep_cmd_modules
+ ; deep_cmd_module(string)
+ ; deep_cmd_top_procs(display_limit, cost_kind, include_descendants,
+ measurement_scope)
+ %
+ % The following commands are for debugging.
+ %
+ ; deep_cmd_proc_static(int)
+ ; deep_cmd_proc_dynamic(int)
+ ; deep_cmd_call_site_static(int)
+ ; deep_cmd_call_site_dynamic(int)
+ ; deep_cmd_raw_clique(int).
+
+:- type caller_groups
+ ---> group_by_call_site
+ ; group_by_proc
+ ; group_by_module
+ ; group_by_clique.
+
+:- type cost_kind
+ ---> cost_calls
+ ; cost_redos
+ ; cost_time
+ ; cost_callseqs
+ ; cost_allocs
+ ; cost_words.
+
+:- type include_descendants
+ ---> self
+ ; self_and_desc.
+
+:- type display_limit
+ ---> rank_range(int, int)
+ % rank_range(M, N): display procedures with rank M to N,
+ % both inclusive.
+
+ ; threshold_percent(float)
+ % threshold(Percent): display procedures whose cost is at least
+ % Percent% of the whole program's cost.
+
+ ; threshold_value(float).
+ % threshold_value(Value): display procedures whose cost is at least
+ % this value.
+
+:- type preferences_indication
+ ---> given_pref(preferences)
+ ; default_pref
+ ; all_pref.
+
+:- type preferences
+ ---> preferences(
+ % The set of fields to display.
+ pref_fields :: fields,
+
+ % Whether displays should be boxed.
+ pref_box :: box,
+
+ % What principle governs colours.
+ pref_colour :: colour_scheme,
+
+ % The max number of ancestors to display.
+ pref_anc :: maybe(int),
+
+ % Whether pages should summarize at higher order call sites.
+ pref_summarize :: summarize,
+
+ % The criteria for ordering lines in pages, if the command
+ % doesn't specify otherwise.
+ pref_criteria :: order_criteria,
+
+ % Whether contour exclusion should be applied.
+ pref_contour :: contour,
+
+ pref_time :: time_format,
+
+ % Whether we should show modules/procs that haven't been called.
+ pref_inactive :: inactive_items
+ ).
+
+:- type port_fields
+ ---> no_port
+ ; port.
+
+:- type time_fields
+ ---> no_time
+ ; ticks
+ ; time
+ ; ticks_and_time
+ ; time_and_percall
+ ; ticks_and_time_and_percall.
+
+
+:- type callseqs_fields
+ ---> no_callseqs
+ ; callseqs
+ ; callseqs_and_percall.
+
+:- type alloc_fields
+ ---> no_alloc
+ ; alloc
+ ; alloc_and_percall.
+
+:- type memory_fields
+ ---> no_memory
+ ; memory(memory_units)
+ ; memory_and_percall(memory_units).
+
+:- type memory_units
+ ---> units_words
+ ; units_bytes.
+
+:- type fields
+ ---> fields(
+ port_fields :: port_fields,
+ time_fields :: time_fields,
+ callseqs_fields :: callseqs_fields,
+ alloc_fields :: alloc_fields,
+ memory_fields :: memory_fields
+ ).
+
+:- type box
+ ---> box
+ ; nobox.
+
+:- type colour_scheme
+ ---> colour_column_groups
+ ; colour_none.
+
+:- type summarize
+ ---> summarize
+ ; dont_summarize.
+
+:- type order_criteria
+ ---> by_context
+ ; by_name
+ ; by_cost(
+ cost_kind,
+ include_descendants,
+ measurement_scope
+ ).
+
+:- type measurement_scope
+ ---> per_call
+ ; overall.
+
+:- type contour
+ ---> apply_contour
+ ; no_contour.
+
+:- type time_format
+ ---> no_scale
+ ; scale_by_millions
+ ; scale_by_thousands.
+
+:- type inactive_status
+ ---> inactive_hide
+ ; inactive_show.
+
+:- type inactive_items
+ ---> inactive_items(
+ inactive_procs :: inactive_status,
+ inactive_modules :: inactive_status
+ ).
+
+%-----------------------------------------------------------------------------%
+
+ % Return "yes" if it is worth displaying times for this profile.
+ %
+:- func should_display_times(deep) = bool.
+
+:- func solidify_preference(deep, preferences_indication) = preferences.
+
+:- func default_preferences(deep) = preferences.
+
+:- func default_fields(deep) = fields.
+:- func all_fields = fields.
+:- func default_box = box.
+:- func default_colour_scheme = colour_scheme.
+:- func default_ancestor_limit = maybe(int).
+:- func default_summarize = summarize.
+:- func default_order_criteria = order_criteria.
+:- func default_cost_kind = cost_kind.
+:- func default_incl_desc = include_descendants.
+:- func default_scope = measurement_scope.
+:- func default_contour = contour.
+:- func default_time_format = time_format.
+:- func default_inactive_items = inactive_items.
+
+:- func query_separator_char = char.
+
+:- func preferences_to_string(preferences) = string.
+:- func cmd_to_string(cmd) = string.
+:- func string_to_cmd(string, cmd) = cmd.
+:- func string_to_maybe_cmd(string) = maybe(cmd).
+:- func string_to_maybe_pref(string) = maybe(preferences).
+
+%-----------------------------------------------------------------------------%
%-----------------------------------------------------------------------------%
:- implementation.
@@ -35,6 +261,7 @@
:- import_module html_format.
:- import_module measurements.
:- import_module top_procs.
+:- import_module util.
:- import_module array.
:- import_module assoc_list.
@@ -1871,6 +2098,11 @@
pair_contour(Deep, ExcludeSpec, CSDPtr) =
apply_contour_exclusion(Deep, ExcludeSpec, CSDPtr) - CSDPtr.
+:- func contour_file_name(string) = string.
+
+contour_file_name(DataFileName) =
+ DataFileName ++ ".contour".
+
%-----------------------------------------------------------------------------%
:- func proc_summary_to_html(preferences, deep, proc_static_ptr) = string.
@@ -2001,6 +2233,617 @@
Str = string.format("<A HREF=%s>%s</A>",
[s(URL), s(escape_break_html_string(Str0))])
).
+%-----------------------------------------------------------------------------%
+
+ % Display times only if the profile was derived from a run that ran for
+ % at least this many quanta.
+ %
+:- func minimum_meaningful_quanta = int.
+
+minimum_meaningful_quanta = 10.
+
+should_display_times(Deep) =
+ ( Deep ^ profile_stats ^ user_quanta > minimum_meaningful_quanta ->
+ yes
+ ;
+ no
+ ).
+
+solidify_preference(Deep, PrefInd) = Pref :-
+ (
+ PrefInd = given_pref(Pref)
+ ;
+ PrefInd = default_pref,
+ Pref = default_preferences(Deep)
+ ;
+ PrefInd = all_pref,
+ Pref = default_preferences(Deep) ^ pref_fields := all_fields
+ ).
+
+default_preferences(Deep) =
+ preferences(
+ default_fields(Deep),
+ default_box,
+ default_colour_scheme,
+ default_ancestor_limit,
+ default_summarize,
+ default_order_criteria,
+ default_contour,
+ default_time_format,
+ default_inactive_items
+ ).
+
+default_fields(Deep) = Fields :-
+ ShouldDisplayTimes = should_display_times(Deep),
+ (
+ ShouldDisplayTimes = yes,
+ Time = ticks
+ ;
+ ShouldDisplayTimes = no,
+ Time = no_time
+ ),
+ Fields = fields(port, Time, callseqs, no_alloc, memory(units_words)).
+all_fields = fields(port, ticks_and_time_and_percall, callseqs_and_percall,
+ alloc, memory(units_words)).
+default_box = box.
+default_colour_scheme = colour_column_groups.
+default_ancestor_limit = yes(5).
+default_summarize = dont_summarize.
+default_order_criteria = by_context.
+default_cost_kind = cost_callseqs.
+default_incl_desc = self_and_desc.
+default_scope = overall.
+default_contour = no_contour.
+default_time_format = scale_by_thousands.
+default_inactive_items = inactive_items(inactive_hide, inactive_hide).
+%-----------------------------------------------------------------------------%
+
+:- func cmd_separator_char = char.
+:- func pref_separator_char = char.
+:- func criteria_separator_char = char.
+:- func field_separator_char = char.
+:- func limit_separator_char = char.
+
+query_separator_char = ('&').
+cmd_separator_char = ('/').
+pref_separator_char = ('/').
+criteria_separator_char = ('-').
+field_separator_char = ('-').
+limit_separator_char = ('-').
+
+%-----------------------------------------------------------------------------%
+
+cmd_to_string(Cmd) = CmdStr :-
+ (
+ Cmd = deep_cmd_quit,
+ CmdStr = "quit"
+ ;
+ Cmd = deep_cmd_restart,
+ CmdStr = "restart"
+ ;
+ Cmd = deep_cmd_timeout(Minutes),
+ CmdStr = string.format("timeout%c%d",
+ [c(cmd_separator_char), i(Minutes)])
+ ;
+ Cmd = deep_cmd_menu,
+ CmdStr = "menu"
+ ;
+ Cmd = deep_cmd_root(MaybePercent),
+ (
+ MaybePercent = yes(Percent),
+ CmdStr = string.format("root%c%d",
+ [c(cmd_separator_char), i(Percent)])
+ ;
+ MaybePercent = no,
+ CmdStr = string.format("root%c%s",
+ [c(cmd_separator_char), s("no")])
+ )
+ ;
+ Cmd = deep_cmd_clique(CliqueNum),
+ CmdStr = string.format("clique%c%d",
+ [c(cmd_separator_char), i(CliqueNum)])
+ ;
+ Cmd = deep_cmd_proc(ProcNum),
+ CmdStr = string.format("proc%c%d",
+ [c(cmd_separator_char), i(ProcNum)])
+ ;
+ Cmd = deep_cmd_proc_callers(ProcNum, GroupCallers, BunchNum),
+ GroupCallersStr = caller_groups_to_string(GroupCallers),
+ CmdStr = string.format("proc_callers%c%d%c%s%c%d",
+ [c(cmd_separator_char), i(ProcNum),
+ c(cmd_separator_char), s(GroupCallersStr),
+ c(cmd_separator_char), i(BunchNum)])
+ ;
+ Cmd = deep_cmd_modules,
+ CmdStr = "modules"
+ ;
+ Cmd = deep_cmd_module(ModuleName),
+ CmdStr = string.format("module%c%s",
+ [c(cmd_separator_char), s(ModuleName)])
+ ;
+ Cmd = deep_cmd_top_procs(Limit, CostKind, InclDesc, Scope),
+ LimitStr = limit_to_string(Limit),
+ CostKindStr = cost_kind_to_string(CostKind),
+ InclDescStr = incl_desc_to_string(InclDesc),
+ ScopeStr = scope_to_string(Scope),
+ CmdStr = string.format("top_procs%c%s%c%s%c%s%c%s",
+ [c(cmd_separator_char), s(LimitStr),
+ c(cmd_separator_char), s(CostKindStr),
+ c(cmd_separator_char), s(InclDescStr),
+ c(cmd_separator_char), s(ScopeStr)])
+ ;
+ Cmd = deep_cmd_proc_static(PSI),
+ CmdStr = string.format("proc_static%c%d",
+ [c(cmd_separator_char), i(PSI)])
+ ;
+ Cmd = deep_cmd_proc_dynamic(PDI),
+ CmdStr = string.format("proc_dynamic%c%d",
+ [c(cmd_separator_char), i(PDI)])
+ ;
+ Cmd = deep_cmd_call_site_static(CSSI),
+ CmdStr = string.format("call_site_static%c%d",
+ [c(cmd_separator_char), i(CSSI)])
+ ;
+ Cmd = deep_cmd_call_site_dynamic(CSDI),
+ CmdStr = string.format("call_site_dynamic%c%d",
+ [c(cmd_separator_char), i(CSDI)])
+ ;
+ Cmd = deep_cmd_raw_clique(CI),
+ CmdStr = string.format("raw_clique%c%d",
+ [c(cmd_separator_char), i(CI)])
+ ).
+
+preferences_to_string(Pref) = PrefStr :-
+ Pref = preferences(Fields, Box, Colour, MaybeAncestorLimit,
+ Summarize, Order, Contour, Time, InactiveItems),
+ (
+ MaybeAncestorLimit = yes(AncestorLimit),
+ MaybeAncestorLimitStr =
+ string.format("%d", [i(AncestorLimit)])
+ ;
+ MaybeAncestorLimit = no,
+ MaybeAncestorLimitStr = "no"
+ ),
+ PrefStr = string.format("%s%c%s%c%s%c%s%c%s%c%s%c%s%c%s%c%s",
+ [s(fields_to_string(Fields)),
+ c(pref_separator_char), s(box_to_string(Box)),
+ c(pref_separator_char), s(colour_scheme_to_string(Colour)),
+ c(pref_separator_char), s(MaybeAncestorLimitStr),
+ c(pref_separator_char), s(summarize_to_string(Summarize)),
+ c(pref_separator_char), s(order_criteria_to_string(Order)),
+ c(pref_separator_char), s(contour_to_string(Contour)),
+ c(pref_separator_char), s(time_format_to_string(Time)),
+ c(pref_separator_char),
+ s(inactive_items_to_string(InactiveItems))
+ ]).
+
+string_to_cmd(QueryString, DefaultCmd) = Cmd :-
+ MaybeCmd = string_to_maybe_cmd(QueryString),
+ (
+ MaybeCmd = yes(Cmd)
+ ;
+ MaybeCmd = no,
+ Cmd = DefaultCmd
+ ).
+
+string_to_maybe_cmd(QueryString) = MaybeCmd :-
+ split(QueryString, pref_separator_char, Pieces),
+ (
+ Pieces = ["root", MaybePercentStr],
+ ( MaybePercentStr = "no" ->
+ MaybePercent = no
+ ; string.to_int(MaybePercentStr, Percent) ->
+ MaybePercent = yes(Percent)
+ ;
+ fail
+ )
+ ->
+ MaybeCmd = yes(deep_cmd_root(MaybePercent))
+ ;
+ Pieces = ["clique", CliqueNumStr],
+ string.to_int(CliqueNumStr, CliqueNum)
+ ->
+ MaybeCmd = yes(deep_cmd_clique(CliqueNum))
+ ;
+ Pieces = ["proc", PSIStr],
+ string.to_int(PSIStr, PSI)
+ ->
+ MaybeCmd = yes(deep_cmd_proc(PSI))
+ ;
+ Pieces = ["proc_callers", PSIStr, GroupCallersStr, BunchNumStr],
+ string.to_int(PSIStr, PSI),
+ string.to_int(BunchNumStr, BunchNum),
+ string_to_caller_groups(GroupCallersStr, GroupCallers)
+ ->
+ MaybeCmd = yes(deep_cmd_proc_callers(PSI, GroupCallers, BunchNum))
+ ;
+ Pieces = ["modules"]
+ ->
+ MaybeCmd = yes(deep_cmd_modules)
+ ;
+ Pieces = ["module", ModuleName]
+ ->
+ MaybeCmd = yes(deep_cmd_module(ModuleName))
+ ;
+ Pieces = ["top_procs", LimitStr, CostKindStr, InclDescStr, ScopeStr],
+ string_to_limit(LimitStr, Limit),
+ string_to_cost_kind(CostKindStr, CostKind),
+ string_to_incl_desc(InclDescStr, InclDesc),
+ string_to_scope(ScopeStr, Scope)
+ ->
+ MaybeCmd = yes(deep_cmd_top_procs(Limit, CostKind, InclDesc, Scope))
+ ;
+ Pieces = ["menu"]
+ ->
+ MaybeCmd = yes(deep_cmd_menu)
+ ;
+ Pieces = ["proc_static", PSIStr],
+ string.to_int(PSIStr, PSI)
+ ->
+ MaybeCmd = yes(deep_cmd_proc_static(PSI))
+ ;
+ Pieces = ["proc_dynamic", PDIStr],
+ string.to_int(PDIStr, PDI)
+ ->
+ MaybeCmd = yes(deep_cmd_proc_dynamic(PDI))
+ ;
+ Pieces = ["call_site_static", CSSIStr],
+ string.to_int(CSSIStr, CSSI)
+ ->
+ MaybeCmd = yes(deep_cmd_call_site_static(CSSI))
+ ;
+ Pieces = ["call_site_dynamic", CSDIStr],
+ string.to_int(CSDIStr, CSDI)
+ ->
+ MaybeCmd = yes(deep_cmd_call_site_dynamic(CSDI))
+ ;
+ Pieces = ["raw_clique", CliqueNumStr],
+ string.to_int(CliqueNumStr, CliqueNum)
+ ->
+ MaybeCmd = yes(deep_cmd_raw_clique(CliqueNum))
+ ;
+ Pieces = ["timeout", TimeOutStr],
+ string.to_int(TimeOutStr, TimeOut)
+ ->
+ MaybeCmd = yes(deep_cmd_timeout(TimeOut))
+ ;
+ Pieces = ["restart"]
+ ->
+ MaybeCmd = yes(deep_cmd_restart)
+ ;
+ Pieces = ["quit"]
+ ->
+ MaybeCmd = yes(deep_cmd_quit)
+ ;
+ MaybeCmd = no
+ ).
+
+string_to_maybe_pref(QueryString) = MaybePreferences :-
+ split(QueryString, pref_separator_char, Pieces),
+ (
+ Pieces = [FieldsStr, BoxStr, ColourStr, MaybeAncestorLimitStr,
+ SummarizeStr, OrderStr, ContourStr, TimeStr,
+ InactiveItemsStr],
+ string_to_fields(FieldsStr, Fields),
+ string_to_box(BoxStr, Box),
+ string_to_colour_scheme(ColourStr, Colour),
+ ( string.to_int(MaybeAncestorLimitStr, AncestorLimit) ->
+ MaybeAncestorLimit = yes(AncestorLimit)
+ ; MaybeAncestorLimitStr = "no" ->
+ MaybeAncestorLimit = no
+ ;
+ fail
+ ),
+ string_to_summarize(SummarizeStr, Summarize),
+ string_to_order_criteria(OrderStr, Order),
+ string_to_contour(ContourStr, Contour),
+ string_to_time_format(TimeStr, Time),
+ string_to_inactive_items(InactiveItemsStr, InactiveItems)
+ ->
+ Preferences = preferences(Fields, Box, Colour, MaybeAncestorLimit,
+ Summarize, Order, Contour, Time, InactiveItems),
+ MaybePreferences = yes(Preferences)
+ ;
+ MaybePreferences = no
+ ).
+
+%-----------------------------------------------------------------------------%
+
+:- func port_fields_to_string(port_fields) = string.
+
+port_fields_to_string(PortFields) = String :-
+ string_to_port_fields(String, PortFields).
+
+:- pred string_to_port_fields(string, port_fields).
+:- mode string_to_port_fields(in, out) is semidet.
+:- mode string_to_port_fields(out, in) is det.
+
+string_to_port_fields("_", no_port).
+string_to_port_fields("p", port).
+
+:- func time_fields_to_string(time_fields) = string.
+
+time_fields_to_string(TimeFields) = String :-
+ string_to_time_fields(String, TimeFields).
+
+:- pred string_to_time_fields(string, time_fields).
+:- mode string_to_time_fields(in, out) is semidet.
+:- mode string_to_time_fields(out, in) is det.
+
+string_to_time_fields("_", no_time).
+string_to_time_fields("q", ticks).
+string_to_time_fields("t", time).
+string_to_time_fields("qt", ticks_and_time).
+string_to_time_fields("tp", time_and_percall).
+string_to_time_fields("qtp", ticks_and_time_and_percall).
+
+:- func callseqs_fields_to_string(callseqs_fields) = string.
+
+callseqs_fields_to_string(AllocFields) = String :-
+ string_to_callseqs_fields(String, AllocFields).
+
+:- pred string_to_callseqs_fields(string, callseqs_fields).
+:- mode string_to_callseqs_fields(in, out) is semidet.
+:- mode string_to_callseqs_fields(out, in) is det.
+
+string_to_callseqs_fields("_", no_callseqs).
+string_to_callseqs_fields("s", callseqs).
+string_to_callseqs_fields("S", callseqs_and_percall).
+
+:- func alloc_fields_to_string(alloc_fields) = string.
+
+alloc_fields_to_string(AllocFields) = String :-
+ string_to_alloc_fields(String, AllocFields).
+
+:- pred string_to_alloc_fields(string, alloc_fields).
+:- mode string_to_alloc_fields(in, out) is semidet.
+:- mode string_to_alloc_fields(out, in) is det.
+
+string_to_alloc_fields("_", no_alloc).
+string_to_alloc_fields("a", alloc).
+string_to_alloc_fields("A", alloc_and_percall).
+
+:- func memory_fields_to_string(memory_fields) = string.
+
+memory_fields_to_string(MemoryFields) = String :-
+ string_to_memory_fields(String, MemoryFields).
+
+:- pred string_to_memory_fields(string, memory_fields).
+:- mode string_to_memory_fields(in, out) is semidet.
+:- mode string_to_memory_fields(out, in) is det.
+
+string_to_memory_fields("_", no_memory).
+string_to_memory_fields("b", memory(units_bytes)).
+string_to_memory_fields("w", memory(units_words)).
+string_to_memory_fields("B", memory_and_percall(units_bytes)).
+string_to_memory_fields("W", memory_and_percall(units_words)).
+
+:- func fields_to_string(fields) = string.
+
+fields_to_string(fields(Port, Time, CallSeqs, Allocs, Memory)) =
+ port_fields_to_string(Port) ++
+ string.char_to_string(field_separator_char) ++
+ time_fields_to_string(Time) ++
+ string.char_to_string(field_separator_char) ++
+ callseqs_fields_to_string(CallSeqs) ++
+ string.char_to_string(field_separator_char) ++
+ alloc_fields_to_string(Allocs) ++
+ string.char_to_string(field_separator_char) ++
+ memory_fields_to_string(Memory).
+
+:- pred string_to_fields(string::in, fields::out) is semidet.
+
+string_to_fields(FieldsStr, Fields) :-
+ (
+ split(FieldsStr, field_separator_char, Pieces),
+ Pieces = [PortStr, TimeStr, CallSeqsStr, AllocStr, MemoryStr],
+ string_to_port_fields(PortStr, Port),
+ string_to_time_fields(TimeStr, Time),
+ string_to_callseqs_fields(CallSeqsStr, CallSeqs),
+ string_to_alloc_fields(AllocStr, Alloc),
+ string_to_memory_fields(MemoryStr, Memory)
+ ->
+ Fields = fields(Port, Time, CallSeqs, Alloc, Memory)
+ ;
+ fail
+ ).
+
+:- func caller_groups_to_string(caller_groups) = string.
+
+caller_groups_to_string(CallerGroups) = String :-
+ string_to_caller_groups(String, CallerGroups).
+
+:- pred string_to_caller_groups(string, caller_groups).
+:- mode string_to_caller_groups(in, out) is semidet.
+:- mode string_to_caller_groups(out, in) is det.
+
+string_to_caller_groups("cs", group_by_call_site).
+string_to_caller_groups("pr", group_by_proc).
+string_to_caller_groups("mo", group_by_module).
+string_to_caller_groups("cl", group_by_clique).
+
+:- func cost_kind_to_string(cost_kind) = string.
+
+cost_kind_to_string(CostKind) = String :-
+ string_to_cost_kind(String, CostKind).
+
+:- pred string_to_cost_kind(string, cost_kind).
+:- mode string_to_cost_kind(in, out) is semidet.
+:- mode string_to_cost_kind(out, in) is det.
+
+string_to_cost_kind("calls", cost_calls).
+string_to_cost_kind("redos", cost_redos).
+string_to_cost_kind("time", cost_time).
+string_to_cost_kind("callseqs", cost_callseqs).
+string_to_cost_kind("allocs", cost_allocs).
+string_to_cost_kind("words", cost_words).
+
+:- func incl_desc_to_string(include_descendants) = string.
+
+incl_desc_to_string(InclDesc) = String :-
+ string_to_incl_desc(String, InclDesc).
+
+:- pred string_to_incl_desc(string, include_descendants).
+:- mode string_to_incl_desc(in, out) is semidet.
+:- mode string_to_incl_desc(out, in) is det.
+
+string_to_incl_desc("self", self).
+string_to_incl_desc("both", self_and_desc).
+
+:- func limit_to_string(display_limit) = string.
+
+limit_to_string(rank_range(Lo, Hi)) =
+ string.format("%d%c%d", [i(Lo), c(limit_separator_char), i(Hi)]).
+limit_to_string(threshold_percent(Threshold)) =
+ string.format("p%g", [f(Threshold)]).
+limit_to_string(threshold_value(Value)) =
+ string.format("v%g", [f(Value)]).
+
+:- pred string_to_limit(string::in, display_limit::out) is semidet.
+
+string_to_limit(LimitStr, Limit) :-
+ (
+ split(LimitStr, limit_separator_char, Pieces),
+ Pieces = [FirstStr, LastStr],
+ string.to_int(FirstStr, First),
+ string.to_int(LastStr, Last)
+ ->
+ Limit = rank_range(First, Last)
+ ;
+ string.append("p", PercentStr, LimitStr),
+ string.to_float(PercentStr, Threshold)
+ ->
+ Limit = threshold_percent(Threshold)
+ ;
+ string.append("v", ValueStr, LimitStr),
+ string.to_float(ValueStr, Value)
+ ->
+ Limit = threshold_value(Value)
+ ;
+ fail
+ ).
+
+:- func summarize_to_string(summarize) = string.
+
+summarize_to_string(summarize) = "sum".
+summarize_to_string(dont_summarize) = "nosum".
+
+:- pred string_to_summarize(string::in, summarize::out) is semidet.
+
+string_to_summarize("sum", summarize).
+string_to_summarize("nosum", dont_summarize).
+
+:- func order_criteria_to_string(order_criteria) = string.
+
+order_criteria_to_string(by_context) = "context".
+order_criteria_to_string(by_name) = "name".
+order_criteria_to_string(by_cost(CostKind, InclDesc, Scope)) =
+ "cost" ++
+ string.char_to_string(criteria_separator_char) ++
+ cost_kind_to_string(CostKind) ++
+ string.char_to_string(criteria_separator_char) ++
+ incl_desc_to_string(InclDesc) ++
+ string.char_to_string(criteria_separator_char) ++
+ scope_to_string(Scope).
+
+:- pred string_to_order_criteria(string::in, order_criteria::out) is semidet.
+
+string_to_order_criteria(CriteriaStr, Criteria) :-
+ (
+ CriteriaStr = "context"
+ ->
+ Criteria = by_context
+ ;
+ CriteriaStr = "name"
+ ->
+ Criteria = by_name
+ ;
+ split(CriteriaStr, criteria_separator_char, Pieces),
+ Pieces = ["cost", CostKindStr, InclDescStr, ScopeStr],
+ string_to_cost_kind(CostKindStr, CostKind),
+ string_to_incl_desc(InclDescStr, InclDesc),
+ string_to_scope(ScopeStr, Scope)
+ ->
+ Criteria = by_cost(CostKind, InclDesc, Scope)
+ ;
+ fail
+ ).
+
+:- func scope_to_string(measurement_scope) = string.
+
+scope_to_string(Scope) = String :-
+ string_to_scope(String, Scope).
+
+:- pred string_to_scope(string, measurement_scope).
+:- mode string_to_scope(in, out) is semidet.
+:- mode string_to_scope(out, in) is det.
+
+string_to_scope("pc", per_call).
+string_to_scope("oa", overall).
+
+:- func contour_to_string(contour) = string.
+
+contour_to_string(Contour) = String :-
+ string_to_contour(String, Contour).
+
+:- pred string_to_contour(string, contour).
+:- mode string_to_contour(in, out) is semidet.
+:- mode string_to_contour(out, in) is det.
+
+string_to_contour("ac", apply_contour).
+string_to_contour("nc", no_contour).
+
+:- func time_format_to_string(time_format) = string.
+
+time_format_to_string(no_scale) = "no".
+time_format_to_string(scale_by_millions) = "mi".
+time_format_to_string(scale_by_thousands) = "th".
+
+:- pred string_to_time_format(string, time_format).
+:- mode string_to_time_format(in, out) is semidet.
+:- mode string_to_time_format(out, in) is det.
+
+string_to_time_format("no", no_scale).
+string_to_time_format("mi", scale_by_millions).
+string_to_time_format("th", scale_by_thousands).
+
+:- func inactive_items_to_string(inactive_items) = string.
+
+inactive_items_to_string(Items) = String :-
+ string_to_inactive_items(String, Items).
+
+:- pred string_to_inactive_items(string, inactive_items).
+:- mode string_to_inactive_items(in, out) is semidet.
+:- mode string_to_inactive_items(out, in) is det.
+
+string_to_inactive_items("hh", inactive_items(inactive_hide, inactive_hide)).
+string_to_inactive_items("sh", inactive_items(inactive_show, inactive_hide)).
+string_to_inactive_items("hs", inactive_items(inactive_hide, inactive_show)).
+string_to_inactive_items("ss", inactive_items(inactive_show, inactive_show)).
+
+:- func colour_scheme_to_string(colour_scheme) = string.
+
+colour_scheme_to_string(Scheme) = String :-
+ string_to_colour_scheme(String, Scheme).
+
+:- pred string_to_colour_scheme(string, colour_scheme).
+:- mode string_to_colour_scheme(in, out) is semidet.
+:- mode string_to_colour_scheme(out, in) is det.
+
+string_to_colour_scheme("cols", colour_column_groups).
+string_to_colour_scheme("none", colour_none).
+
+:- func box_to_string(box) = string.
+
+box_to_string(Box) = String :-
+ string_to_box(String, Box).
+
+:- pred string_to_box(string, box).
+:- mode string_to_box(in, out) is semidet.
+:- mode string_to_box(out, in) is det.
+
+string_to_box("box", box).
+string_to_box("nobox", nobox).
%----------------------------------------------------------------------------%
:- end_module query.
Index: deep_profiler/top_procs.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/deep_profiler/top_procs.m,v
retrieving revision 1.12
diff -u -u -r1.12 top_procs.m
--- deep_profiler/top_procs.m 23 Nov 2007 07:35:52 -0000 1.12
+++ deep_profiler/top_procs.m 18 Apr 2008 02:41:37 -0000
@@ -18,9 +18,9 @@
:- module top_procs.
:- interface.
-:- import_module interface.
:- import_module measurements.
:- import_module profile.
+:- import_module query.
:- import_module list.
:- import_module maybe.
--------------------------------------------------------------------------
mercury-reviews mailing list
Post messages to: mercury-reviews at csse.unimelb.edu.au
Administrative Queries: owner-mercury-reviews at csse.unimelb.edu.au
Subscriptions: mercury-reviews-request at csse.unimelb.edu.au
--------------------------------------------------------------------------
More information about the reviews
mailing list