3030 scheduling_delay_busy /1 ,
3131 scheduling_delay_busy_nosuspend /1 ,
3232 scheduling_busy_link /1 ,
33- busy_with_signals /1 ]).
33+ busy_with_signals /1 ,
34+ async_par_nosuspend_abort_cleanup /1 ,
35+ async_nopar_nosuspend_abort_cleanup /1 ,
36+ sync_par_nosuspend_abort_cleanup /1 ,
37+ sync_nopar_nosuspend_abort_cleanup /1 ]).
3438
3539-include_lib (" common_test/include/ct.hrl" ).
3640
@@ -46,7 +50,11 @@ all() ->
4650 no_trap_exit , no_trap_exit_unlinked , trap_exit ,
4751 multiple_writers , hard_busy_driver , soft_busy_driver ,
4852 scheduling_delay_busy ,scheduling_delay_busy_nosuspend ,
49- scheduling_busy_link , busy_with_signals ].
53+ scheduling_busy_link , busy_with_signals ,
54+ async_par_nosuspend_abort_cleanup ,
55+ async_nopar_nosuspend_abort_cleanup ,
56+ sync_par_nosuspend_abort_cleanup ,
57+ sync_nopar_nosuspend_abort_cleanup ].
5058
5159init_per_testcase (_Case , Config ) when is_list (Config ) ->
5260 Killer = spawn (fun () -> killer_loop ([]) end ),
@@ -846,6 +854,69 @@ flood_with_exit_signals(Pid, N) ->
846854 exit (Pid , pling ),
847855 flood_with_exit_signals (Pid , N - 1 ).
848856
857+ async_par_nosuspend_abort_cleanup (Config ) when is_list (Config ) ->
858+ nosuspend_abort_cleanup_tests (Config , false , true ).
859+
860+ async_nopar_nosuspend_abort_cleanup (Config ) when is_list (Config ) ->
861+ nosuspend_abort_cleanup_tests (Config , false , false ).
862+
863+ sync_par_nosuspend_abort_cleanup (Config ) when is_list (Config ) ->
864+ nosuspend_abort_cleanup_tests (Config , true , true ).
865+
866+ sync_nopar_nosuspend_abort_cleanup (Config ) when is_list (Config ) ->
867+ nosuspend_abort_cleanup_tests (Config , true , false ).
868+
869+ nosuspend_abort_cleanup_tests (Config , Sync , Parallelism ) ->
870+ Master = self (),
871+ process_flag (priority ,high ),
872+ Drv = " nosuspend_test_drv" ,
873+ DataDir = proplists :get_value (data_dir , Config ),
874+ erl_ddll :start (),
875+ case erl_ddll :load_driver (DataDir , Drv ) of
876+ ok ->
877+ ok ;
878+ {error , Error } ->
879+ ct :fail (erl_ddll :format_error (Error ))
880+ end ,
881+ Port = open_port ({spawn_driver , Drv },
882+ [{busy_limits_msgq , {1024 , 2048 }},
883+ {parallelism , Parallelism }]),
884+ NoSuspFun = if Sync ->
885+ fun () ->
886+ port_command (Port , <<0 :(16 * 8 * 1024 )>>, [nosuspend ])
887+ end ;
888+ true ->
889+ fun () ->
890+ erlang :send (Port ,
891+ {Master , {command , <<0 :(16 * 8 * 1024 )>>}},
892+ [nosuspend ])
893+ end
894+ end ,
895+ NoSuspers = lists :map (fun (_ ) -> spawn_link (NoSuspFun ) end ,
896+ lists :seq (1 , 10000 )),
897+ _ = port_control (Port , $B , <<>>),
898+ receive after 1000 -> ok end ,
899+ _ = port_control (Port , $N , <<>>),
900+ SyncCmd = spawn_link (fun () ->
901+ port_command (Port , <<" should not block for long" >>),
902+ Master ! {self (), done }
903+ end ),
904+ receive
905+ {SyncCmd , done } -> ok
906+ after
907+ 10000 -> ct :fail (port_command_blocked )
908+ end ,
909+ lists :foreach (fun (P ) ->
910+ unlink (P ),
911+ exit (P ,kill ),
912+ false = is_process_alive (P )
913+ end ,
914+ [SyncCmd | NoSuspers ]),
915+ true = erlang :port_close (Port ),
916+ ok = erl_ddll :unload_driver (Drv ),
917+ ok = erl_ddll :stop (),
918+ ok .
919+
849920% %% Utilities.
850921
851922pal (_F ,_A ) -> ok .
0 commit comments