anchor.diff:      [{timetrap, {seconds, 10}}].
   
   all() ->
  -    [send_not_from_controlling_process,
  -     send_from_multiple_clients,
  +    [send_one_from_many,
  +     send_many_from_one,
        receive_what_was_sent].
   
   init_per_suite(Config) ->
  
positive.code: 
  %% ===========================================================================
  
  %% send_not_from_controlling_process/1
  %%
  %% This testcase failing shows gen_sctp:send/4 hanging when called
  %% outside the controlling process of the socket in question.
  
  send_not_from_controlling_process(_) ->
      Pids = send_not_from_controlling_process(),
      ?SLEEP(?FOREVER),
      try
          [] = [{P,I} || P <- Pids, I <- [process_info(P)], I /= undefined]
      after
          lists:foreach(fun(P) -> exit(P, kill) end, Pids)
      end.
  
  %% send_not_from_controlling_process/0
  %%
  %% Returns the pids of three spawned processes: a listening process, a
  %% connecting process and a sending process.
  %%
  %% The expected behaviour is that all three processes exit:
  %%
  %% - The listening process exits upon receiving an SCTP message
  %%   sent by the sending process.
  %% - The connecting process exits upon listening process exit.
  %% - The sending process exits upon gen_sctp:send/4 return.
  %%
  %% The observed behaviour is that all three processes remain alive
  %% indefinitely:
  %%
  %% - The listening process never receives the SCTP message sent
  %%   by the sending process.
  %% - The connecting process has an inet_reply message in its mailbox
  %%   as a consequence of the call to gen_sctp:send/4 call from the
  %%   sending process.
  %% - The call to gen_sctp:send/4 in the sending process doesn't return,
  %%   hanging in prim_inet:getopts/2.
  
  send_not_from_controlling_process() ->
      FPid = self(),
      {L, MRef} = spawn_monitor(fun() -> listen(FPid) end),
      receive
          {?MODULE, C, S} ->
              demonitor(MRef, [flush]),
              [L,C,S];
          {'DOWN', MRef, process, _, _} = T ->
              error(T)
      end.
  
  %% listen/1
  
  listen(FPid) ->
      {ok, Sock} = open(),
      ok = gen_sctp:listen(Sock, true),
      {ok, PortNr} = inet:port(Sock),
      LPid = self(),
      spawn(fun() -> connect1(PortNr, FPid, LPid) end), %% connecting process
      Id = assoc(Sock),
      recv(Sock, Id).
  
  %% connect1/3
  
  connect1(PortNr, FPid, LPid) ->
      {ok, Sock} = open(),
      ok = gen_sctp:connect_init(Sock, ?ADDR, PortNr, []),
      Id = assoc(Sock),
      FPid ! {?MODULE,
              self(),
              spawn(fun() -> send(Sock, Id) end)}, %% sending process
      MRef = monitor(process, LPid),
      down(MRef).  %% Waits with this as current_function.
  
  %% down/1
  
  down(MRef) ->
      receive {'DOWN', MRef, process, _, Reason} -> Reason end.
  
  %% send/2
  
  send(Sock, Id) ->
      ok = gen_sctp:send(Sock, Id, 0, <<0:32>>).
  
  %% ===========================================================================
  
  %% send_from_multiple_clients/0
  %%
  %% Demonstrates sluggish delivery of messages.
  
  send_from_multiple_clients() ->
      [{timetrap, {seconds, 60}}].
  
  send_from_multiple_clients(_) ->
      {S, Rs} = T = send_from_multiple_clients(8, 1024),
      Max = ?FOREVER*1000,
      {false, [], _} = {Max < S,
                        Rs -- [OI || {O,_} = OI <- Rs, is_integer(O)],
                        T}.
  
  %% send_from_multiple_clients/2
  %%
  %% Opens a listening socket and then spawns a specified number of
  %% processes, each of which connects to the listening socket. Each
  %% connecting process then sends a message, whose size in bytes is
  %% passed as an argument, the listening process sends a reply
  %% containing the time at which the message was received, and the
  %% connecting process then exits upon reception of this reply.
  %%
  %% Returns the elapsed time for all connecting process to exit
  %% together with a list of exit reasons for the connecting processes.
  %% In the successful case a connecting process exits with the
  %% outbound/inbound transit times for the sent/received message as
  %% reason.
  %%
  %% The observed behaviour is that some outbound messages (that is,
  %% from a connecting process to the listening process) can take an
  %% unexpectedly long time to complete their journey. The more
  %% connecting processes, the longer the possible delay it seems.
  %%
  %% eg. (With F = fun send_from_multiple_clients/2.)
  %%
  %%     5> F(2, 1024).
  %%     {875,[{128,116},{113,139}]}
  %%     6> F(4, 1024).
  %%     {2995290,[{2994022,250},{2994071,80},{200,130},{211,113}]}
  %%     7> F(8, 1024).
  %%     {8997461,[{8996161,116},
  %%               {2996471,86},
  %%               {2996278,116},
  
negative.code: %%
  %% %CopyrightBegin%
  %%
  %% Copyright Ericsson AB 2010-2017. All Rights Reserved.
  %%
  %% Licensed under the Apache License, Version 2.0 (the "License");
  %% you may not use this file except in compliance with the License.
  