problem with new socket module setopt()

Raimo Niskanen raimo+erlang-questions@REDACTED
Fri Jan 29 10:22:10 CET 2021


On Thu, Jan 28, 2021 at 01:18:55PM -0700, Mark Geib wrote:
> Adding socket:setopt(Socket, otp, debug, true) did not seem to have any effect. I captured a snippet from the log below which may help.
> 
> 2021-01-28T09:08:04.897919-08:00 [error] Supervisor: {local,ptc_6254_A_transport_sup}. Context: start_error. Reason: {badarg,[{prim_socket,nif_setopt,[#Ref<0.2135233317.2669019137.87142>,true,303,3002,#{interface => {172,24,4,30},multiaddr => {239,33,62,54},sourceaddr => {172,24,93,7}}],[]},{cse_socket,open_ssm_mc,
> 4,[{file,"/home/geib/git/cse.mpeg.invidi.pts_delta/apps/ipd/src/cse_socket.erl"},{line,87}]},{mpeg_ingest_rtp,init,1,[{file,"/home/geib/git/cse.mpeg.invidi.pts_delta/apps/ipd/src/mpeg_ingest_rtp.erl"},{line,49}]},{gen_server,init_it,2,[{file,"gen_server.erl"},{line,417}]},{gen_server,init_it,6,[{file,"gen_server.er
> l"},{line,385}]},{proc_lib,init_p_do_apply,3,[{file,"proc_lib.erl"},{line,226}]}]}. Offender: id=ptc_6254_A,pid=undefined.

This is a bug that was accidentally fixed in a code cleanup on the master
branch, so it will not be present in OTP 24.0.

There are redundant checks on the map value, and one of them
is wrong; the size check is inverted.

This patch should fix the issue:

--- a/erts/emulator/nifs/common/prim_socket_nif.c
+++ b/erts/emulator/nifs/common/prim_socket_nif.c
@@ -10931,21 +10931,12 @@ ERL_NIF_TERM
esock_setopt_lvl_ip_update_source(ErlNifEnv*       env,
     struct ip_mreq_source mreq;
     char*                 xres;
     int                   res;
-    size_t                sz;
 #if defined(SOL_IP)
     int            level = SOL_IP;
 #else
     int            level = IPPROTO_IP;
 #endif
 
-    // It must be a map
-    if (!IS_MAP(env, eVal))
-        return enif_make_badarg(env);
-
-    // It must have atleast three attributes
-    if (!enif_get_map_size(env, eVal, &sz) || (sz >= 3))
-        return enif_make_badarg(env);
-
     if (!GET_MAP_VAL(env, eVal, atom_multiaddr, &eMultiAddr))
         return enif_make_badarg(env);

GET_MAP_VAL itself checks that it eVal a map, and the size is verified by the
fact that there are 3 of them.

And this would be a minimal patch; a 2=>1 chars patch:

--- a/erts/emulator/nifs/common/prim_socket_nif.c
+++ b/erts/emulator/nifs/common/prim_socket_nif.c
@@ -10943,7 +10943,7 @@ ERL_NIF_TERM
esock_setopt_lvl_ip_update_source(ErlNifEnv*       env,
         return enif_make_badarg(env);
 
     // It must have atleast three attributes
-    if (!enif_get_map_size(env, eVal, &sz) || (sz >= 3))
+    if (!enif_get_map_size(env, eVal, &sz) || (sz < 3))
         return enif_make_badarg(env);
 
     if (!GET_MAP_VAL(env, eVal, atom_multiaddr, &eMultiAddr))

/ Raimo


> 
> Mark.
> 
> 
> > On Jan 28, 2021, at 10:27 AM, Micael Karlberg <micael.karlberg@REDACTED> wrote:
> > 
> > Before the call to the setopt, add a call to socket:setopt(Socket, otp, debug, true).
> > 
> > /BMK
> > 
> > 
> > From: erlang-questions on behalf of Mark Geib
> > Sent: Thursday, January 28, 2021 6:24 PM
> > To: Erlang Questions
> > Subject: problem with new socket module setopt()
> > 
> > I am using the new socket module in order to join a source-specific multicast and receive datagrams. The following code fails with a “badarg” error on the socket:setopt() call. I have carefully checked the docs for R23, but can not find the problem.
> > 
> >     {ok, GroupAddr} = inet:getaddr(Group, inet),
> >     {ok, SourceAddr} = inet:getaddr(Source, inet),
> >     {ok, IfAddr} = inet:getaddr(Interface, inet),
> >     IpMreqSource = #{multiaddr => GroupAddr,
> >                      interface => IfAddr,
> >                      sourceaddr => SourceAddr},
> > 
> >     {ok, Socket} = socket:open(inet, dgram, udp),
> >     {ok, Port} = socket:bind(Socket, #{family => inet, port => Port, addr => GroupAddr}),
> >     ok = socket:setopt(Socket, ip, add_source_membership,  IpMreqSource),
> > 
> > I am using Erlang R23, latest release on debian-9 host.
> > Any suggestions would be appreciated greatly.
> > 
> > Mark.
> 



-- 

/ Raimo Niskanen, Erlang/OTP, Ericsson AB


More information about the erlang-questions mailing list