diff options
Diffstat (limited to 'lib/debugger/src')
-rw-r--r-- | lib/debugger/src/dbg_debugged.erl | 14 | ||||
-rw-r--r-- | lib/debugger/src/dbg_ieval.erl | 105 | ||||
-rw-r--r-- | lib/debugger/src/dbg_istk.erl | 2 | ||||
-rw-r--r-- | lib/debugger/src/dbg_wx_mon.erl | 93 | ||||
-rw-r--r-- | lib/debugger/src/dbg_wx_mon_win.erl | 72 | ||||
-rw-r--r-- | lib/debugger/src/dbg_wx_trace.erl | 83 | ||||
-rw-r--r-- | lib/debugger/src/dbg_wx_trace_win.erl | 17 | ||||
-rw-r--r-- | lib/debugger/src/dbg_wx_win.erl | 2 |
8 files changed, 259 insertions, 129 deletions
diff --git a/lib/debugger/src/dbg_debugged.erl b/lib/debugger/src/dbg_debugged.erl index c21ad486e8..d8285d7288 100644 --- a/lib/debugger/src/dbg_debugged.erl +++ b/lib/debugger/src/dbg_debugged.erl @@ -19,8 +19,6 @@ -module(dbg_debugged). %% External exports -%% Avoid warning for local function demonitor/1 clashing with autoimported BIF. --compile({no_auto_import,[demonitor/1]}). -export([eval/3]). %%==================================================================== @@ -47,7 +45,7 @@ msg_loop(Meta, Mref, SaveStacktrace) -> %% Evaluated function has returned a value {sys, Meta, {ready, Val}} -> - demonitor(Mref), + erlang:demonitor(Mref, [flush]), %% Restore original stacktrace and return the value try erlang:raise(throw, stack, SaveStacktrace) @@ -63,7 +61,7 @@ msg_loop(Meta, Mref, SaveStacktrace) -> %% Evaluated function raised an (uncaught) exception {sys, Meta, {exception,{Class,Reason,Stacktrace}}} -> - demonitor(Mref), + erlang:demonitor(Mref, [flush]), %% ...raise the same exception erlang:error(erlang:raise(Class, Reason, Stacktrace), @@ -107,14 +105,6 @@ reply({eval,Expr,Bs}) -> %% Bindings is an orddict (sort them) erl_eval:expr(Expr, lists:sort(Bs)). % {value, Value, Bs2} -%% Demonitor and delete message from inbox -%% -demonitor(Mref) -> - erlang:demonitor(Mref), - receive {'DOWN',Mref,_,_,_} -> ok - after 0 -> ok - end. - %% Fix stacktrace - keep all above call to this module. %% stacktrace_f([]) -> []; diff --git a/lib/debugger/src/dbg_ieval.erl b/lib/debugger/src/dbg_ieval.erl index f5744a6e14..f4b6d488a5 100644 --- a/lib/debugger/src/dbg_ieval.erl +++ b/lib/debugger/src/dbg_ieval.erl @@ -324,61 +324,64 @@ trace(What, Args) -> trace(return, {_Le,{dbg_apply,_,_,_}}, _Bool) -> ignore; trace(What, Args, true) -> - Str = case What of - send -> - {To,Msg} = Args, - io_lib:format("==> ~w : ~p~n", [To, Msg]); - receivex -> - {Le, TimeoutP} = Args, - Tail = case TimeoutP of - true -> "with timeout~n"; - false -> "~n" - end, - io_lib:format(" (~w) receive " ++ Tail, [Le]); - - received when Args =:= null -> - io_lib:format("~n", []); - received -> % Args=Msg - io_lib:format("~n<== ~p~n", [Args]); - - call -> - {Called, {Le,Li,M,F,As}} = Args, - case Called of - extern -> - io_lib:format("++ (~w) <~w> ~w:~w~ts~n", - [Le,Li,M,F,format_args(As)]); - local -> - io_lib:format("++ (~w) <~w> ~w~ts~n", - [Le,Li,F,format_args(As)]) - end; - call_fun -> - {Le,Li,F,As} = Args, - io_lib:format("++ (~w) <~w> ~w~ts~n", - [Le, Li, F, format_args(As)]); - return -> - {Le,Val} = Args, - io_lib:format("-- (~w) ~p~n", [Le, Val]); - - - bif -> - {Le,Li,M,F,As} = Args, - io_lib:format("++ (~w) <~w> ~w:~w~ts~n", - [Le, Li, M, F, format_args(As)]) - end, - dbg_icmd:tell_attached({trace_output, Str}); + Fun = fun(P) -> format_trace(What, Args, P) end, + dbg_icmd:tell_attached({trace_output, Fun}); trace(_What, _Args, false) -> ignore. -format_args(As) when is_list(As) -> - [$(,format_args1(As),$)]; -format_args(A) -> - [$/,io_lib:format("~p", [A])]. +format_trace(What, Args, P) -> + case What of + send -> + {To,Msg} = Args, + io_lib:format("==> ~w : "++P++"~n", [To, Msg]); + receivex -> + {Le, TimeoutP} = Args, + Tail = case TimeoutP of + true -> "with timeout~n"; + false -> "~n" + end, + io_lib:format(" (~w) receive " ++ Tail, [Le]); + + received when Args =:= null -> + io_lib:format("~n", []); + received -> % Args=Msg + io_lib:format("~n<== "++P++"~n", [Args]); + + call -> + {Called, {Le,Li,M,F,As}} = Args, + case Called of + extern -> + io_lib:format("++ (~w) <~w> ~w:~w~ts~n", + [Le,Li,M,F,format_args(As, P)]); + local -> + io_lib:format("++ (~w) <~w> ~w~ts~n", + [Le,Li,F,format_args(As, P)]) + end; + call_fun -> + {Le,Li,F,As} = Args, + io_lib:format("++ (~w) <~w> ~w~ts~n", + [Le, Li, F, format_args(As, P)]); + return -> + {Le,Val} = Args, + io_lib:format("-- (~w) "++P++"~n", [Le, Val]); + + + bif -> + {Le,Li,M,F,As} = Args, + io_lib:format("++ (~w) <~w> ~w:~w~ts~n", + [Le, Li, M, F, format_args(As, P)]) + end. + +format_args(As, P) when is_list(As) -> + [$(,format_args1(As, P),$)]; +format_args(A, P) -> + [$/,io_lib:format(P, [A])]. -format_args1([A]) -> - [io_lib:format("~p", [A])]; -format_args1([A|As]) -> - [io_lib:format("~p", [A]),$,|format_args1(As)]; -format_args1([]) -> +format_args1([A], P) -> + [io_lib:format(P, [A])]; +format_args1([A|As], P) -> + [io_lib:format(P, [A]),$,|format_args1(As, P)]; +format_args1([], _) -> []. %%--Other useful functions-------------------------------------------- diff --git a/lib/debugger/src/dbg_istk.erl b/lib/debugger/src/dbg_istk.erl index c6922a80e4..ced42a5f9f 100644 --- a/lib/debugger/src/dbg_istk.erl +++ b/lib/debugger/src/dbg_istk.erl @@ -78,7 +78,7 @@ push(Bs, #ieval{level=Le,module=Mod,function=Name, pop() -> case get(trace_stack) of false -> ignore; - _ -> % all ¦ no_tail + _ -> % all | no_tail case get(?STACK) of [_Entry|Entries] -> put(?STACK, Entries); diff --git a/lib/debugger/src/dbg_wx_mon.erl b/lib/debugger/src/dbg_wx_mon.erl index 6bdec994b1..4a01492cf5 100644 --- a/lib/debugger/src/dbg_wx_mon.erl +++ b/lib/debugger/src/dbg_wx_mon.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2008-2010. All Rights Reserved. +%% Copyright Ericsson AB 2008-2013. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -28,6 +28,9 @@ -define(TRACEWIN, ['Search Area', 'Button Area', 'Evaluator Area', 'Bindings Area']). -define(BACKTRACE, 100). +-define(STRNAME, 'Use range of +pc flag'). % See also erl(1) +-define(STRINGS, [str_on]). +-define(AUTO_ATTACH, [init, exit, break]). -record(pinfo, {pid, % pid() status % break | exit | idle | running | waiting @@ -45,6 +48,7 @@ tracewin, % [Area] Areas shown in trace window backtrace, % integer() Number of call frames to fetch + strings, % [str_on] Integer lists as strings attach, % false | {Flags, Function} @@ -157,6 +161,7 @@ init2(CallingPid, Mode, SFile, GS) -> int:auto_attach(), % Auto Attach int:stack_trace(), % Stack Trace ?BACKTRACE, % Back Trace Size + ?STRINGS, % Lists as Strings State1), State3 = init_contents(int:interpreted(), % Modules @@ -176,7 +181,7 @@ init2(CallingPid, Mode, SFile, GS) -> loop(load_settings(SFile, State3)) end. -init_options(TraceWin, AutoAttach, StackTrace, BackTrace, State) -> +init_options(TraceWin, AutoAttach, StackTrace, BackTrace, Strings, State) -> lists:foreach(fun(Area) -> dbg_wx_mon_win:select(Area, true) end, @@ -187,10 +192,7 @@ init_options(TraceWin, AutoAttach, StackTrace, BackTrace, State) -> {Flags, _Function} -> dbg_wx_mon_win:show_option(State#state.win, auto_attach, Flags), - lists:foreach(fun(Flag) -> - dbg_wx_mon_win:select(map(Flag), true) - end, - Flags) + select(Flags, ?AUTO_ATTACH) end, dbg_wx_mon_win:show_option(State#state.win, @@ -199,7 +201,10 @@ init_options(TraceWin, AutoAttach, StackTrace, BackTrace, State) -> dbg_wx_mon_win:show_option(State#state.win, back_trace, BackTrace), - State#state{tracewin=TraceWin, backtrace=BackTrace}. + select(Strings, ?STRINGS), + dbg_wx_mon_win:show_option(State#state.win, strings, Strings), + + State#state{tracewin=TraceWin, backtrace=BackTrace, strings=Strings}. init_contents(Mods, Breaks, Processes, State) -> Win2 = @@ -431,7 +436,7 @@ gui_cmd({'Stack Trace', [Name]}, State) -> State; gui_cmd('Back Trace Size...', State) -> Window = dbg_wx_mon_win:get_window(State#state.win), - What = {integer, State#state.backtrace}, + What = {integer, integer_to_list(State#state.backtrace)}, case dbg_wx_win:entry(Window, "Backtrace", 'Backtrace:', What) of cancel -> State; @@ -439,6 +444,11 @@ gui_cmd('Back Trace Size...', State) -> dbg_wx_mon_win:show_option(State#state.win,back_trace, BackTrace), State#state{backtrace=BackTrace} end; +gui_cmd({'Strings', Flags}, State) -> + Names = [map(Flag) || Flag <- Flags], + dbg_wx_mon_win:show_option(State#state.win, strings, Names), + select(Names, ?STRINGS), + State#state{strings=Names}; %% Help Menu gui_cmd('Debugger', State) -> @@ -522,16 +532,8 @@ int_cmd({auto_attach, AutoAttach}, State) -> false -> []; {Flags, _Function} -> Flags end, - OffFlags = [init, exit, break] -- OnFlags, dbg_wx_mon_win:show_option(State#state.win, auto_attach, OnFlags), - lists:foreach(fun(Flag) -> - dbg_wx_mon_win:select(map(Flag), true) - end, - OnFlags), - lists:foreach(fun(Flag) -> - dbg_wx_mon_win:select(map(Flag), false) - end, - OffFlags), + select(OnFlags, ?AUTO_ATTACH), State#state{attach=AutoAttach}; int_cmd({stack_trace, Flag}, State) -> dbg_wx_mon_win:show_option(State#state.win, stack_trace, Flag), @@ -582,6 +584,8 @@ menus() -> [{'Stack On, Tail', no, radio}, {'Stack On, No Tail', no, radio}, {'Stack Off', no, radio}]}, + {'Strings', no, cascade, + [{?STRNAME, no, check}]}, {'Back Trace Size...', no}]}, {'Windows', []}, {'Help', [{'Debugger', no}]}]. @@ -642,8 +646,21 @@ map('Stack Off') -> false; map(all) -> 'Stack On, Tail'; map(true) -> 'Stack On, Tail'; map(no_tail) -> 'Stack On, No Tail'; -map(false) -> 'Stack Off'. +map(false) -> 'Stack Off'; + +map(?STRNAME) -> str_on; % Strings +map(str_on) -> ?STRNAME. +select(Flags, AllFlags) -> + OffFlags = AllFlags -- Flags, + lists:foreach(fun(Flag) -> + dbg_wx_mon_win:select(map(Flag), false) + end, + OffFlags), + lists:foreach(fun(Flag) -> + dbg_wx_mon_win:select(map(Flag), true) + end, + Flags). %%==================================================================== %% Debugger settings @@ -663,8 +680,8 @@ load_settings(SFile, State) -> end. load_settings2(Settings, State) -> - {TraceWin, AutoAttach, StackTrace, BackTrace, Files, Breaks} = - Settings, + Vals = loaded(Settings), + [TraceWin,AutoAttach,StackTrace,BackTrace,Strings,Files,Breaks] = Vals, TraceWinAll = ['Button Area', 'Evaluator Area', 'Bindings Area', 'Trace Area'], @@ -680,6 +697,13 @@ load_settings2(Settings, State) -> int:stack_trace(StackTrace), + if + Strings =:= keep -> ok; + true -> + dbg_wx_mon_win:show_option(State#state.win, strings, Strings), + select(Strings, ?STRINGS) + end, + dbg_wx_mon_win:show_option(State#state.win, back_trace, BackTrace), case State#state.mode of @@ -708,16 +732,18 @@ load_settings2(Settings, State) -> end, Breaks), - State#state{tracewin=TraceWin, backtrace=BackTrace}. + State#state{tracewin=TraceWin, backtrace=BackTrace, strings=Strings}. -save_settings(SFile, State) -> - Settings = {State#state.tracewin, - int:auto_attach(), - int:stack_trace(), - State#state.backtrace, - [int:file(Mod) || Mod <- int:interpreted()], - int:all_breaks()}, +loaded({TraceWin, AutoAttach, StackTrace, BackTrace, Files, Breaks}) -> + %% Up to and including R16B + [TraceWin,AutoAttach,StackTrace,BackTrace,keep,Files,Breaks]; +loaded(Settings) when is_list(Settings) -> + Keys = [trace_win,auto_attach,stack_trace,back_trace,strings,files, + breaks], + [proplists:get_value(Key, Settings) || Key <- Keys]. +save_settings(SFile, State) -> + Settings = saved(State), Binary = term_to_binary({debugger_settings, Settings}), case file:write_file(SFile, Binary) of ok -> @@ -726,6 +752,14 @@ save_settings(SFile, State) -> State end. +saved(#state{tracewin=TraceWin, backtrace=BackTrace, strings=Strings}) -> + [{trace_win,TraceWin}, + {auto_attach,int:auto_attach()}, + {stack_trace,int:stack_trace()}, + {back_trace,BackTrace}, + {strings,Strings}, + {files,[int:file(Mod) || Mod <- int:interpreted()]}, + {breaks,int:all_breaks()}]. %%==================================================================== %% Other internal functions @@ -752,4 +786,5 @@ registered_name(Pid) -> end. trace_function(State) -> - {dbg_wx_trace, start, [State#state.tracewin, State#state.backtrace]}. + #state{tracewin=Win, backtrace=BT, strings=Str} = State, + {dbg_wx_trace, start, [Win,BT,Str]}. diff --git a/lib/debugger/src/dbg_wx_mon_win.erl b/lib/debugger/src/dbg_wx_mon_win.erl index 04c3501b8c..a617f3e1e7 100644 --- a/lib/debugger/src/dbg_wx_mon_win.erl +++ b/lib/debugger/src/dbg_wx_mon_win.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 2008-2010. All Rights Reserved. +%% Copyright Ericsson AB 2008-2013. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -36,6 +36,8 @@ -include_lib("wx/include/wx.hrl"). +-define(STRTEXT, "Use range of +pc flag"). + -define(default_rows,10). -record(moduleInfo, {module, menubtn}). @@ -60,6 +62,9 @@ ebutton, % gsobj() selected=[], % ['First Call'|'On Break'|'On Exit'] + %% Strings button(s) + stringsbutton,% gsobj() + slabel, % showing Stack Trace option blabel % showing Back Trace Size }). @@ -86,6 +91,10 @@ init() -> -define(W, 800). -define(H, 390). +%% FIXME +-define(autoId, 314). +-define(stringsId, 271). + create_win(_Wx, Title, Menus) -> wx:batch(fun() -> create_win_batch(Title, Menus) end). @@ -104,19 +113,19 @@ create_win_batch(Title, Menus) -> Hlb = 200, Listbox = wxListBox:new(Panel, ?wxID_ANY, [{size,{?Wf,Hlb}}, {style,?wxLB_SINGLE}]), - wxSizer:add(LeftSz,Listbox,[{proportion,1}, {border,3}]), + wxSizer:add(LeftSz,Listbox,[{proportion,1},{border,3},{flag,?wxEXPAND}]), wxListBox:connect(Listbox, command_listbox_doubleclicked), wxListBox:connect(Listbox, right_down), SBox = wxStaticBox:new(Panel, ?wxID_ANY, "Auto Attach:"), SBS = wxStaticBoxSizer:new(SBox, ?wxVERTICAL), - Fbtn = wxCheckBox:new(Panel, ?wxID_ANY, "First Call"), + Fbtn = wxCheckBox:new(Panel, ?autoId, "First Call"), wxSizer:add(SBS,Fbtn), - Bbtn = wxCheckBox:new(Panel, ?wxID_ANY, "On Break"), + Bbtn = wxCheckBox:new(Panel, ?autoId, "On Break"), wxSizer:add(SBS,Bbtn), - Ebtn = wxCheckBox:new(Panel, ?wxID_ANY, "On Exit"), + Ebtn = wxCheckBox:new(Panel, ?autoId, "On Exit"), wxSizer:add(SBS,Ebtn), - wxFrame:connect(Panel, command_checkbox_clicked), + wxFrame:connect(Panel, command_checkbox_clicked), wxSizer:add(LeftSz,SBS, [{flag,?wxEXPAND}]), SLabel = wxStaticText:new(Panel, ?wxID_ANY, "Stack Trace:\n On (with tail)"), @@ -124,6 +133,12 @@ create_win_batch(Title, Menus) -> BLabel = wxStaticText:new(Panel, ?wxID_ANY, "Back Trace Size:\n 50000"), wxSizer:add(LeftSz,BLabel), + StringsBox = wxStaticBox:new(Panel, ?wxID_ANY, "Strings:"), + StringsBS = wxStaticBoxSizer:new(StringsBox, ?wxVERTICAL), + Stringsbtn = wxCheckBox:new(Panel, ?stringsId, ?STRTEXT), + wxSizer:add(StringsBS,Stringsbtn), + wxSizer:add(LeftSz,StringsBS, [{flag,?wxEXPAND}]), + %% Create list_crtl / grid Grid = wxListCtrl:new(Panel, [{winid, ?GRID}, {style, ?wxLC_REPORT bor ?wxLC_SINGLE_SEL @@ -177,6 +192,7 @@ create_win_batch(Title, Menus) -> #winInfo{window=Win, grid=Grid, row=0, focus=0, listbox=Listbox, fbutton=Fbtn, bbutton=Bbtn, ebutton=Ebtn, + stringsbutton=Stringsbtn, slabel=SLabel, blabel=BLabel}. %%-------------------------------------------------------------------- @@ -190,11 +206,13 @@ get_window(WinInfo) -> %%-------------------------------------------------------------------- %% show_option(WinInfo, Option, Value) -> void() %% WinInfo = #winInfo{} -%% Option = auto_attach | stack_trace | back_trace +%% Option = auto_attach | stack_trace | back_trace | strings %% Value = [Flag] % Option==auto_attach %% Flag = init | break | exit %% | true | all | no_tail | false % Option==stack_trace -%% | int() % Option==back_trace +%% | integer() % Option==back_trace +%% | [SFlag] % Option==strings +%% SFlag = str_on %%-------------------------------------------------------------------- show_option(WinInfo, Option, Value) -> case Option of @@ -219,15 +237,28 @@ show_option(WinInfo, Option, Value) -> back_trace -> Text = "Back Trace Size:\n " ++ integer_to_list(Value), - wxStaticText:setLabel(WinInfo#winInfo.blabel, Text) + wxStaticText:setLabel(WinInfo#winInfo.blabel, Text); + strings -> + wx:foreach(fun(Button) -> + wxCheckBox:setValue(Button, false) + end, + option_buttons(WinInfo, [str_on])), + wx:foreach(fun(Button) -> + wxCheckBox:setValue(Button, true) + end, + option_buttons(WinInfo, Value)) end. +%% Auto Attach option_buttons(WinInfo, [init|Flags]) -> [WinInfo#winInfo.fbutton|option_buttons(WinInfo, Flags)]; option_buttons(WinInfo, [break|Flags]) -> [WinInfo#winInfo.bbutton|option_buttons(WinInfo, Flags)]; option_buttons(WinInfo, [exit|Flags]) -> [WinInfo#winInfo.ebutton|option_buttons(WinInfo, Flags)]; +%% Strings +option_buttons(WinInfo, [str_on|Flags]) -> + [WinInfo#winInfo.stringsbutton|option_buttons(WinInfo, Flags)]; option_buttons(_WinInfo, []) -> []. @@ -538,7 +569,8 @@ handle_event(#wx{obj=ListBox, event=#wxMouse{type=right_down, x=X,y=Y}}, end; %% Auto attach buttons -handle_event(#wx{event=#wxCommand{type=command_checkbox_clicked}}, +handle_event(#wx{id=?autoId, + event=#wxCommand{type=command_checkbox_clicked}}, WinInfo) -> Check = fun(Button, NamesAcc) -> case wxCheckBox:isChecked(Button) of @@ -555,6 +587,23 @@ handle_event(#wx{event=#wxCommand{type=command_checkbox_clicked}}, WinInfo#winInfo.fbutton]), {'Auto Attach', Names}; +%% Strings button(s) +handle_event(#wx{id=?stringsId, + event=#wxCommand{type=command_checkbox_clicked}}, + WinInfo) -> + Check = fun(Button, NamesAcc) -> + case wxCheckBox:isChecked(Button) of + true -> + Name = wxCheckBox:getLabel(Button), + [list_to_atom(Name)|NamesAcc]; + false -> + NamesAcc + end + end, + Names = wx:foldl(Check, [], + [WinInfo#winInfo.stringsbutton]), + {'Strings', Names}; + %% Process grid handle_event(#wx{event=#wxList{type=command_list_item_selected, itemIndex=Row}}, WinInfo) -> @@ -575,7 +624,8 @@ handle_event(#wx{userData=Data, _WinInfo) -> Data; handle_event(_Event, _WinInfo) -> -%% io:format("Ev: ~p~n",[_Event]), +%% FIXME + io:format("Ev: ~p~n",[_Event]), ignore. %%==================================================================== diff --git a/lib/debugger/src/dbg_wx_trace.erl b/lib/debugger/src/dbg_wx_trace.erl index eaea01822c..7108b5a79a 100644 --- a/lib/debugger/src/dbg_wx_trace.erl +++ b/lib/debugger/src/dbg_wx_trace.erl @@ -21,11 +21,13 @@ -module(dbg_wx_trace). %% External exports --export([start/1, start/3]). +-export([start/1, start/3, start/4]). -export([title/1]). -define(TRACEWIN, ['Button Area', 'Evaluator Area', 'Bindings Area']). -define(BACKTRACE, 100). +-define(STRNAME, 'Use range of +pc flag'). % See also erl(1) +-define(STRINGS, [str_on]). -record(state, {win, % term() Attach process window data coords, % {X,Y} Mouse point position @@ -45,7 +47,8 @@ trace, % boolean() stack_trace, % all | no_tail | false - backtrace % integer() #call frames to fetch + backtrace, % integer() #call frames to fetch + strings % [str_on] Integer lists as strings }). %%==================================================================== @@ -62,8 +65,12 @@ %% Backtrace = integer() %%-------------------------------------------------------------------- start(Pid) -> % Used by debugger:quick/3 (no monitor) - start(Pid, ?TRACEWIN, ?BACKTRACE). -start(Pid, TraceWin, BackTrace) -> + start(Pid, ?TRACEWIN, ?BACKTRACE, ?STRINGS). + +start(Pid, TraceWin, BackTrace) -> + start(Pid, TraceWin, BackTrace, ?STRINGS). + +start(Pid, TraceWin, BackTrace, Strings) -> case {whereis(dbg_wx_mon), whereis(dbg_ui_mon)} of {undefined, undefined} -> case which_gui() of @@ -72,7 +79,7 @@ start(Pid, TraceWin, BackTrace) -> wx -> Parent = wx:new(), Env = wx:get_env(), - start(Pid, Env, Parent, TraceWin, BackTrace) + start(Pid, Env, Parent, TraceWin, BackTrace, Strings) end; {undefined, Monitor} when is_pid(Monitor) -> dbg_ui_trace:start(Pid, TraceWin, BackTrace); @@ -80,17 +87,17 @@ start(Pid, TraceWin, BackTrace) -> Monitor ! {?MODULE, self(), get_env}, receive {env, Monitor, Env, Parent} -> - start(Pid, Env, Parent, TraceWin, BackTrace) + start(Pid, Env, Parent, TraceWin, BackTrace, Strings) end end. -start(Pid, Env, Parent, TraceWin, BackTrace) -> +start(Pid, Env, Parent, TraceWin, BackTrace, Strings) -> %% Inform int about my existence and get the meta pid back case int:attached(Pid) of {ok, Meta} -> try wx:set_env(Env), - init(Pid, Parent, Meta, TraceWin, BackTrace) + init(Pid, Parent, Meta, TraceWin, BackTrace, Strings) catch _:stop -> exit(stop); @@ -126,7 +133,7 @@ title(Pid) -> %% Main loop and message handling %%==================================================================== -init(Pid, Parent, Meta, TraceWin, BackTrace) -> +init(Pid, Parent, Meta, TraceWin, BackTrace, Strings) -> %% Start necessary stuff dbg_wx_trace_win:init(), % Graphics system @@ -140,11 +147,12 @@ init(Pid, Parent, Meta, TraceWin, BackTrace) -> %% Initial process state State1 = #state{win=Win, coords={0,0}, pid=Pid, meta=Meta, status={idle,null,null}, - stack={1,1}}, + stack={1,1}, strings=[str_on]}, State2 = init_options(TraceWin, int:stack_trace(), % Stack Trace BackTrace, % Back trace size + Strings, % Strings State1), State3 = init_contents(int:all_breaks(), % Breakpoints @@ -158,7 +166,7 @@ init(Pid, Parent, Meta, TraceWin, BackTrace) -> loop(State3). -init_options(TraceWin, StackTrace, BackTrace, State) -> +init_options(TraceWin, StackTrace, BackTrace, Strings, State) -> lists:foreach(fun(Area) -> dbg_wx_trace_win:select(Area, true) end, TraceWin), @@ -166,9 +174,16 @@ init_options(TraceWin, StackTrace, BackTrace, State) -> dbg_wx_trace_win:select(map(StackTrace), true), + lists:foreach(fun(Flag) -> + dbg_wx_trace_win:select(map(Flag), true) + end, + Strings), + dbg_wx_trace_win:update_strings(Strings), + %% Backtrace size is (currently) not shown in window - State#state{trace=Trace,stack_trace=StackTrace,backtrace=BackTrace}. + State#state{trace=Trace,stack_trace=StackTrace,backtrace=BackTrace, + strings=Strings}. init_contents(Breaks, State) -> Win = @@ -331,8 +346,9 @@ gui_cmd('Messages', State) -> fun(Msg, N) -> Str1 = io_lib:format(" ~w:", [N]), dbg_wx_trace_win:eval_output(State#state.win,Str1, bold), - Str2 = io_lib:format(" ~ts~n",[io_lib:print(Msg)]), - dbg_wx_trace_win:eval_output(State#state.win,Str2, normal), + Str2 = pretty(Msg, State), + Str3 = io_lib:format(" ~ts~n",[Str2]), + dbg_wx_trace_win:eval_output(State#state.win,Str3, normal), N+1 end, 1, @@ -341,13 +357,14 @@ gui_cmd('Messages', State) -> State; gui_cmd('Back Trace', State) -> dbg_wx_trace_win:trace_output(State#state.win,"\nBACK TRACE\n----------\n"), + P = p(State), lists:foreach( fun({Le, {Mod,Func,Args}}) -> - Str = io_lib:format("~p > ~p:~p~p~n", + Str = io_lib:format("~p > ~p:~p"++P++"~n", [Le, Mod, Func, Args]), dbg_wx_trace_win:trace_output(State#state.win,Str); ({Le, {Fun,Args}}) -> - Str = io_lib:format("~p > ~p~p~n", [Le, Fun, Args]), + Str = io_lib:format("~p > ~p"++P++"~n", [Le, Fun, Args]), dbg_wx_trace_win:trace_output(State#state.win,Str); (_) -> ignore end, @@ -474,10 +491,15 @@ gui_cmd({'Stack Trace', [Name]}, State) -> State; gui_cmd('Back Trace Size...', State) -> Win = dbg_wx_trace_win:get_window(State#state.win), - case dbg_wx_win:entry(Win, "Backtrace",'Backtrace:', {integer, State#state.backtrace}) of + Val = integer_to_list(State#state.backtrace), + case dbg_wx_win:entry(Win, "Backtrace",'Backtrace:', {integer, Val}) of cancel -> State; {_, BackTrace} -> State#state{backtrace=BackTrace} end; +gui_cmd({'Strings', Flags}, State) -> + Names = [map(Flag) || Flag <- Flags], + dbg_wx_trace_win:update_strings(Names), + State#state{strings=Names}; %% Help menu gui_cmd('Debugger', State) -> @@ -507,8 +529,12 @@ gui_cmd({user_command, Cmd}, State) -> end, State; -gui_cmd({edit, {Var, Val}}, State) -> +gui_cmd({edit, {Var, Value}}, State) -> Window = dbg_wx_trace_win:get_window(State#state.win), + Val = case State#state.strings of + [] -> dbg_wx_win:to_string("~999999lp",[Value]); + [str_on] -> dbg_wx_win:to_string("~999999tp",[Value]) + end, case dbg_wx_win:entry(Window, "Edit variable", Var, {term, Val}) of cancel -> State; @@ -681,16 +707,23 @@ meta_cmd({stack_trace, Flag}, State) -> end, State#state{stack_trace=Flag}; -meta_cmd({trace_output, Str}, State) -> - dbg_wx_trace_win:trace_output(State#state.win, Str), +meta_cmd({trace_output, StrFun}, State) -> + P = p(State), + dbg_wx_trace_win:trace_output(State#state.win, StrFun(P)), State; %% Reply on a user command meta_cmd({eval_rsp, Res}, State) -> - Str = io_lib_pretty:print(Res,[{encoding,unicode}]), + Str = pretty(Res, State), dbg_wx_trace_win:eval_output(State#state.win, [$<,Str,10], normal), State. +pretty(Term, State) -> + Strings = case State#state.strings of + [str_on] -> true; + [] -> false + end, + io_lib_pretty:print(Term,[{encoding,unicode},{strings,Strings}]). %%==================================================================== %% GUI auxiliary functions @@ -734,6 +767,8 @@ menus() -> [{'Stack On, Tail', no, radio}, {'Stack On, No Tail', no, radio}, {'Stack Off', no, radio}]}, + {'Strings', no, cascade, + [{?STRNAME, no, check}]}, {'Back Trace Size...', no}]}, {'Windows', []}, {'Help', [{'Debugger', no}]}]. @@ -774,8 +809,12 @@ map('Stack Off') -> false; map(all) -> 'Stack On, Tail'; map(true) -> 'Stack On, Tail'; map(no_tail) -> 'Stack On, No Tail'; -map(false) -> 'Stack Off'. +map(false) -> 'Stack Off'; +map(?STRNAME) -> str_on; % Strings +map(str_on) -> ?STRNAME. +p(#state{strings=[str_on]}) -> "~tp"; +p(#state{strings=[]}) -> "~lp". %% gui_show_module(Win, Mod, Line, Cm, Pid, How) -> Win %% gui_show_module(Win, {Mod,Line}, _Reason, Cm, Pid, How) -> Win diff --git a/lib/debugger/src/dbg_wx_trace_win.erl b/lib/debugger/src/dbg_wx_trace_win.erl index e54ce3913f..48935c66a5 100644 --- a/lib/debugger/src/dbg_wx_trace_win.erl +++ b/lib/debugger/src/dbg_wx_trace_win.erl @@ -35,6 +35,7 @@ select_line/2, selected_line/1, eval_output/3, % Evaluator area update_bindings/2, % Bindings area + update_strings/1, trace_output/2, % Trace area handle_event/2 ]). @@ -200,6 +201,7 @@ create_win(Parent, Title, Windows, Menus) -> wxFrame:show(Win), put(window, Win), + put(strings, [str_on]), Wi end, @@ -567,12 +569,20 @@ update_bindings(#winInfo{bind=#sub{out=BA}}, Bs) -> wx:foldl(fun({Var,Val},Row) -> wxListCtrl:insertItem(BA, Row, ""), wxListCtrl:setItem(BA, Row, 0, dbg_wx_win:to_string(Var)), - wxListCtrl:setItem(BA, Row, 1, dbg_wx_win:to_string("~99999tP",[Val, 20])), + Format = case get(strings) of + [] -> "~999999lP"; + [str_on] -> "~999999tP" + end, + wxListCtrl:setItem(BA, Row, 1, dbg_wx_win:to_string(Format,[Val, 20])), Row+1 end, 0, Bs), put(bindings,Bs), ok. +update_strings(Strings) -> + _ = put(strings, Strings), + ok. + %%-------------------------------------------------------------------- %% trace_output(Str) %% Str = string() @@ -853,7 +863,10 @@ handle_event(#wx{id=?EVAL_ENTRY, event=#wxCommand{type=command_text_enter}}, handle_event(#wx{event=#wxList{type=command_list_item_selected, itemIndex=Row}},Wi) -> Bs = get(bindings), {Var,Val} = lists:nth(Row+1, Bs), - Str = io_lib:format("< ~s = ~lp~n", [Var, Val]), + Str = case get(strings) of + [] -> io_lib:format("< ~s = ~lp~n", [Var, Val]); + [str_on] -> io_lib:format("< ~s = ~tp~n", [Var, Val]) + end, eval_output(Wi, Str, bold), ignore; handle_event(#wx{event=#wxList{type=command_list_item_activated, itemIndex=Row}},_Wi) -> diff --git a/lib/debugger/src/dbg_wx_win.erl b/lib/debugger/src/dbg_wx_win.erl index eceacd7c88..65b2a0ebea 100644 --- a/lib/debugger/src/dbg_wx_win.erl +++ b/lib/debugger/src/dbg_wx_win.erl @@ -254,7 +254,7 @@ notify(Win,Message) -> entry(Parent, Title, Prompt, {Type, Value}) -> Ted = wxTextEntryDialog:new(Parent, to_string(Prompt), [{caption, to_string(Title)}, - {value, to_string("~999999tp",[Value])}]), + {value, Value}]), case wxDialog:showModal(Ted) of ?wxID_OK -> |