aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMicael Karlberg <[email protected]>2018-07-19 14:36:34 +0200
committerMicael Karlberg <[email protected]>2018-09-18 14:50:18 +0200
commitf0a2e68a31ac585780ad05f777f1b7551770420e (patch)
treea45d1a46e617e7d71142b3ce5e87504ca33c3515
parentd28129b7098bce154264937862fcdafb21541433 (diff)
downloadotp-f0a2e68a31ac585780ad05f777f1b7551770420e.tar.gz
otp-f0a2e68a31ac585780ad05f777f1b7551770420e.tar.bz2
otp-f0a2e68a31ac585780ad05f777f1b7551770420e.zip
[socket-nif] Add support for socket (level sctp) option disable_fragments
Added support for the SCTP option DISABLE_FRAGMENTS. OTP-14831
-rw-r--r--erts/doc/src/socket_usage.xml7
-rw-r--r--erts/emulator/nifs/common/socket_nif.c53
-rw-r--r--erts/preloaded/ebin/socket.beambin52584 -> 52640 bytes
-rw-r--r--erts/preloaded/src/socket.erl9
-rw-r--r--lib/kernel/test/socket_server.erl27
5 files changed, 80 insertions, 16 deletions
diff --git a/erts/doc/src/socket_usage.xml b/erts/doc/src/socket_usage.xml
index 1d7b98d1a3..9f25e2e9b9 100644
--- a/erts/doc/src/socket_usage.xml
+++ b/erts/doc/src/socket_usage.xml
@@ -459,6 +459,13 @@
<cell>none</cell>
</row>
<row>
+ <cell>disable_fragments</cell>
+ <cell>boolean()</cell>
+ <cell>yes</cell>
+ <cell>yes</cell>
+ <cell>none</cell>
+ </row>
+ <row>
<cell>events</cell>
<cell>sctp_event_subscribe()</cell>
<cell>yes</cell>
diff --git a/erts/emulator/nifs/common/socket_nif.c b/erts/emulator/nifs/common/socket_nif.c
index 7271db2143..2a60a840c8 100644
--- a/erts/emulator/nifs/common/socket_nif.c
+++ b/erts/emulator/nifs/common/socket_nif.c
@@ -542,9 +542,10 @@ typedef union {
#define SOCKET_OPT_UDP_CORK 1
-#define SOCKET_OPT_SCTP_AUTOCLOSE 8
-#define SOCKET_OPT_SCTP_EVENTS 14
-#define SOCKET_OPT_SCTP_NODELAY 23
+#define SOCKET_OPT_SCTP_AUTOCLOSE 8
+#define SOCKET_OPT_SCTP_DISABLE_FRAGMENTS 12
+#define SOCKET_OPT_SCTP_EVENTS 14
+#define SOCKET_OPT_SCTP_NODELAY 23
/* =================================================================== *
@@ -1216,6 +1217,11 @@ static ERL_NIF_TERM nsetopt_lvl_sctp_autoclose(ErlNifEnv* env,
SocketDescriptor* descP,
ERL_NIF_TERM eVal);
#endif
+#if defined(SCTP_DISABLE_FRAGMENTS)
+static ERL_NIF_TERM nsetopt_lvl_sctp_disable_fragments(ErlNifEnv* env,
+ SocketDescriptor* descP,
+ ERL_NIF_TERM eVal);
+#endif
#if defined(SCTP_EVENTS)
static ERL_NIF_TERM nsetopt_lvl_sctp_events(ErlNifEnv* env,
SocketDescriptor* descP,
@@ -1433,6 +1439,10 @@ static ERL_NIF_TERM ngetopt_lvl_sctp(ErlNifEnv* env,
static ERL_NIF_TERM ngetopt_lvl_sctp_autoclose(ErlNifEnv* env,
SocketDescriptor* descP);
#endif
+#if defined(SCTP_DISABLE_FRAGMENTS)
+static ERL_NIF_TERM ngetopt_lvl_sctp_disable_fragments(ErlNifEnv* env,
+ SocketDescriptor* descP);
+#endif
#if defined(SCTP_NODELAY)
static ERL_NIF_TERM ngetopt_lvl_sctp_nodelay(ErlNifEnv* env,
SocketDescriptor* descP);
@@ -5509,6 +5519,12 @@ ERL_NIF_TERM nsetopt_lvl_sctp(ErlNifEnv* env,
break;
#endif
+#if defined(SCTP_DISABLE_FRAGMENTS)
+ case SOCKET_OPT_SCTP_DISABLE_FRAGMENTS:
+ result = nsetopt_lvl_sctp_disable_fragments(env, descP, eVal);
+ break;
+#endif
+
#if defined(SCTP_EVENTS)
case SOCKET_OPT_SCTP_EVENTS:
result = nsetopt_lvl_sctp_events(env, descP, eVal);
@@ -5543,6 +5559,19 @@ ERL_NIF_TERM nsetopt_lvl_sctp_autoclose(ErlNifEnv* env,
#endif
+/* nsetopt_lvl_sctp_disable_fragments - Level SCTP DISABLE_FRAGMENTS option
+ */
+#if defined(SCTP_DISABLE_FRAGMENTS)
+static
+ERL_NIF_TERM nsetopt_lvl_sctp_disable_fragments(ErlNifEnv* env,
+ SocketDescriptor* descP,
+ ERL_NIF_TERM eVal)
+{
+ return nsetopt_bool_opt(env, descP, IPPROTO_SCTP, SCTP_DISABLE_FRAGMENTS, eVal);
+}
+#endif
+
+
/* nsetopt_lvl_sctp_events - Level SCTP EVENTS option
*/
#if defined(SCTP_EVENTS)
@@ -7308,6 +7337,12 @@ ERL_NIF_TERM ngetopt_lvl_sctp(ErlNifEnv* env,
break;
#endif
+#if defined(SCTP_DISABLE_FRAGMENTS)
+ case SOCKET_OPT_SCTP_DISABLE_FRAGMENTS:
+ result = ngetopt_lvl_sctp_disable_fragments(env, descP);
+ break;
+#endif
+
#if defined(SCTP_NODELAY)
case SOCKET_OPT_SCTP_NODELAY:
result = ngetopt_lvl_sctp_nodelay(env, descP);
@@ -7335,6 +7370,18 @@ ERL_NIF_TERM ngetopt_lvl_sctp_autoclose(ErlNifEnv* env,
#endif
+/* ngetopt_lvl_sctp_disable_fragments - Level SCTP DISABLE:FRAGMENTS option
+ */
+#if defined(SCTP_DISABLE_FRAGMENTS)
+static
+ERL_NIF_TERM ngetopt_lvl_sctp_disable_fragments(ErlNifEnv* env,
+ SocketDescriptor* descP)
+{
+ return ngetopt_bool_opt(env, descP, IPPROTO_SCTP, SCTP_DISABLE_FRAGMENTS);
+}
+#endif
+
+
/* ngetopt_lvl_sctp_nodelay - Level SCTP NODELAY option
*/
#if defined(SCTP_NODELAY)
diff --git a/erts/preloaded/ebin/socket.beam b/erts/preloaded/ebin/socket.beam
index fd62a18a49..63887692f9 100644
--- a/erts/preloaded/ebin/socket.beam
+++ b/erts/preloaded/ebin/socket.beam
Binary files differ
diff --git a/erts/preloaded/src/socket.erl b/erts/preloaded/src/socket.erl
index 74b6bfd543..e3fb417a35 100644
--- a/erts/preloaded/src/socket.erl
+++ b/erts/preloaded/src/socket.erl
@@ -647,7 +647,7 @@
%% -define(SOCKET_OPT_SCTP_CONTEXT, 9).
%% -define(SOCKET_OPT_SCTP_DEFAULT_SEND_PARAMS, 10).
%% -define(SOCKET_OPT_SCTP_DELAYED_ACK_TIME, 11).
-%% -define(SOCKET_OPT_SCTP_DISABLE_FRAGMENTS, 12).
+-define(SOCKET_OPT_SCTP_DISABLE_FRAGMENTS, 12).
%% -define(SOCKET_OPT_SCTP_HMAC_IDENT, 13).
-define(SOCKET_OPT_SCTP_EVENTS, 14).
%% -define(SOCKET_OPT_SCTP_EXPLICIT_EOR, 15).
@@ -2175,6 +2175,9 @@ enc_setopt_value(udp = L, Opt, _V, _D, _T, _P) ->
enc_setopt_value(sctp, autoclose, V, _D, _T, P)
when is_integer(V) andalso (P =:= sctp) ->
V;
+enc_setopt_value(sctp, disable_fragments, V, _D, _T, P)
+ when is_boolean(V) andalso (P =:= sctp) ->
+ V;
enc_setopt_value(sctp, events, #{data_in := DataIn,
association := Assoc,
address := Addr,
@@ -2612,8 +2615,8 @@ enc_sockopt_key(sctp = L, default_send_params = Opt, _Dir, _D, _T, _P) ->
not_supported({L, Opt});
enc_sockopt_key(sctp = L, delayed_ack_time = Opt, _Dir, _D, _T, _P) ->
not_supported({L, Opt});
-enc_sockopt_key(sctp = L, disable_fragments = Opt, _Dir, _D, _T, _P) ->
- not_supported({L, Opt});
+enc_sockopt_key(sctp = _L, disable_fragments = _Opt, _Dir, _D, _T, _P) ->
+ ?SOCKET_OPT_SCTP_DISABLE_FRAGMENTS;
enc_sockopt_key(sctp = L, hmac_ident = Opt, _Dir, _D, _T, _P) ->
not_supported({L, Opt});
enc_sockopt_key(sctp = _L, events = _Opt, set = _Dir, _D, _T, _P) ->
diff --git a/lib/kernel/test/socket_server.erl b/lib/kernel/test/socket_server.erl
index 23f30a0d03..a9b4aca5f8 100644
--- a/lib/kernel/test/socket_server.erl
+++ b/lib/kernel/test/socket_server.erl
@@ -187,14 +187,21 @@ do_manager_init(Domain, seqpacket = Type, sctp = Proto, _Peek) ->
{ok, Sock} ->
i("(sctp) socket opened: "
"~n ~p", [Sock]),
- F = fun(_Desc, Expect, Expect) ->
- Expect;
- (Desc, Expect, Actual) ->
- e("Unexpected result ~w: "
- "~n Expect: ~p"
- "~n Actual: ~p", [Desc, Expect, Actual]),
- exit({Desc, Expect, Actual})
- end,
+ EXP = fun(_Desc, Expect, Expect) ->
+ Expect;
+ (Desc, Expect, Actual) ->
+ e("Unexpected result ~w: "
+ "~n Expect: ~p"
+ "~n Actual: ~p", [Desc, Expect, Actual]),
+ exit({Desc, Expect, Actual})
+ end,
+ GO = fun(O) -> case socket:getopt(Sock, sctp, O) of
+ {ok, V} -> f("~p", [V]);
+ {error, R} -> f("error: ~p", [R])
+ end
+ end,
+ i("Miscellaneous options: "
+ "~n disable-fragments: ~s", [GO(disable_fragments)]),
Events = #{data_in => true,
association => true,
address => true,
@@ -205,8 +212,8 @@ do_manager_init(Domain, seqpacket = Type, sctp = Proto, _Peek) ->
adaptation_layer => true,
authentication => true,
sender_dry => true},
- F(set_sctp_events, ok, socket:setopt(Sock, sctp, events, Events)),
- F(close_socket, ok, socket:close(Sock));
+ EXP(set_sctp_events, ok, socket:setopt(Sock, sctp, events, Events)),
+ EXP(close_socket, ok, socket:close(Sock));
{error, Reason} ->
exit({failed_open, Reason})
end.