aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorErlang/OTP <[email protected]>2019-07-02 13:44:03 +0200
committerErlang/OTP <[email protected]>2019-07-02 13:44:03 +0200
commit72f271c15f3c95b32340103e497477ee5983280a (patch)
tree592d93bca277ff1ba14639f1fad4f3d52b02a820
parente02ab342939b6fe11090950137966542df82650f (diff)
parent7d1058ed7de3c04055feb62108a78e29c33c5ddb (diff)
downloadotp-72f271c15f3c95b32340103e497477ee5983280a.tar.gz
otp-72f271c15f3c95b32340103e497477ee5983280a.tar.bz2
otp-72f271c15f3c95b32340103e497477ee5983280a.zip
Merge branch 'sverker/system_info-procs-bug/ERL-979/OTP-15909' into maint-22
* sverker/system_info-procs-bug/ERL-979/OTP-15909: Fix fatal bug in erts_proc_sig_signal_size
-rw-r--r--erts/emulator/beam/erl_proc_sig_queue.c1
-rw-r--r--erts/emulator/test/system_info_SUITE.erl53
2 files changed, 54 insertions, 0 deletions
diff --git a/erts/emulator/beam/erl_proc_sig_queue.c b/erts/emulator/beam/erl_proc_sig_queue.c
index f58a606d57..55e469b553 100644
--- a/erts/emulator/beam/erl_proc_sig_queue.c
+++ b/erts/emulator/beam/erl_proc_sig_queue.c
@@ -4051,6 +4051,7 @@ erts_proc_sig_signal_size(ErtsSignal *sig)
case ERTS_MON_TYPE_DIST_PROC:
case ERTS_MON_TYPE_NODE:
size = erts_monitor_size((ErtsMonitor *) sig);
+ break;
default:
ERTS_INTERNAL_ERROR("Unexpected sig type");
break;
diff --git a/erts/emulator/test/system_info_SUITE.erl b/erts/emulator/test/system_info_SUITE.erl
index 55b1162cfb..b48be3dd04 100644
--- a/erts/emulator/test/system_info_SUITE.erl
+++ b/erts/emulator/test/system_info_SUITE.erl
@@ -37,10 +37,13 @@
-export([process_count/1, system_version/1, misc_smoke_tests/1,
heap_size/1, wordsize/1, memory/1, ets_limit/1, atom_limit/1,
+ procs_bug/1,
ets_count/1, atom_count/1, system_logger/1]).
-export([init/1, handle_event/2, handle_call/2]).
+-export([init_per_testcase/2, end_per_testcase/2]).
+
suite() ->
[{ct_hooks,[ts_install_cth]},
{timetrap, {minutes, 2}}].
@@ -48,8 +51,20 @@ suite() ->
all() ->
[process_count, system_version, misc_smoke_tests,
ets_count, heap_size, wordsize, memory, ets_limit, atom_limit, atom_count,
+ procs_bug,
system_logger].
+
+init_per_testcase(procs_bug, Config) ->
+ procs_bug(init_per_testcase, Config);
+init_per_testcase(_, Config) ->
+ Config.
+
+end_per_testcase(procs_bug, Config) ->
+ procs_bug(end_per_testcase, Config);
+end_per_testcase(_, _) ->
+ ok.
+
%%%
%%% The test cases -------------------------------------------------------------
%%%
@@ -654,3 +669,41 @@ handle_call(Msg, State) ->
handle_event(Event, State) ->
State ! {report_handler, Event},
{ok, State}.
+
+
+%% OTP-15909: Provoke bug that would cause VM crash
+%% if doing system_info(procs) when process have queued exit/down signals.
+procs_bug(init_per_testcase, Config) ->
+ %% Use single scheduler and process prio to starve monitoring processes
+ %% from handling their received DOWN signals.
+ OldSchedOnline = erlang:system_flag(schedulers_online,1),
+ [{schedulers_online, OldSchedOnline} | Config];
+procs_bug(end_per_testcase, Config) ->
+ erlang:system_flag(schedulers_online,
+ proplists:get_value(schedulers_online, Config)),
+ ok.
+
+procs_bug(Config) when is_list(Config) ->
+ {Monee,_} = spawn_opt(fun () -> receive die -> ok end end,
+ [monitor,{priority,max}]),
+ Papa = self(),
+ Pids = [begin
+ P = spawn_opt(fun () ->
+ erlang:monitor(process, Monee),
+ Papa ! {self(),ready},
+ receive "nada" -> no end
+ end,
+ [link, {priority,normal}]),
+ {P, ready} = receive M -> M end,
+ P
+ end
+ || _ <- lists:seq(1,10)],
+ process_flag(priority,high),
+ Monee ! die,
+ {'DOWN',_,process,Monee,normal} = receive M -> M end,
+
+ %% This call did crash VM as Pids have pending DOWN signals.
+ erlang:system_info(procs),
+ process_flag(priority,normal),
+ [begin unlink(P), exit(P, kill) end || P <- Pids],
+ ok.