Skip to content

Commit

Permalink
Merge branch 'msantos/epmd-IPv6-node-reg2/PR-864/OTP-13364' into maint
Browse files Browse the repository at this point in the history
* msantos/epmd-IPv6-node-reg2/PR-864/OTP-13364:
  epmd: support IPv6 node registration
  • Loading branch information
IngelaAndin committed Mar 1, 2016
2 parents 6f8997c + 40695d0 commit 75bc5be
Show file tree
Hide file tree
Showing 11 changed files with 279 additions and 104 deletions.
2 changes: 1 addition & 1 deletion erts/configure.in
Original file line number Diff line number Diff line change
Expand Up @@ -468,7 +468,7 @@ case $host_os in
win32)
# The ethread library requires _WIN32_WINNT of at least 0x0403.
# -D_WIN32_WINNT=* from CPPFLAGS is saved in ETHR_DEFS.
CPPFLAGS="$CPPFLAGS -D_WIN32_WINNT=0x0501 -DWINVER=0x0501"
CPPFLAGS="$CPPFLAGS -D_WIN32_WINNT=0x0600 -DWINVER=0x0600"
;;
darwin*)
CPPFLAGS="$CPPFLAGS -D_XOPEN_SOURCE"
Expand Down
2 changes: 1 addition & 1 deletion erts/doc/src/epmd.xml
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@
<comsummary>
<p>Erlang Port Mapper Daemon</p>
<taglist>
<tag><c><![CDATA[epmd [-d|-debug] [DbgExtra...] [-port No] [-daemon] [-relaxed_command_check]]]></c></tag>
<tag><c><![CDATA[epmd [-d|-debug] [DbgExtra...] [-address Addresses] [-port No] [-daemon] [-relaxed_command_check]]]></c></tag>
<item>
<p>Starts the port mapper daemon</p>
</item>
Expand Down
22 changes: 22 additions & 0 deletions erts/doc/src/erl.xml
Original file line number Diff line number Diff line change
Expand Up @@ -387,6 +387,28 @@
<p>Replaces the path specified in the boot script. See
<seealso marker="sasl:script">script(4)</seealso>.</p>
</item>
<tag><c><![CDATA[-proto_dist Proto]]></c></tag>
<item>
<p>Specify a protocol for Erlang distribution.</p>
<taglist>
<tag><c>inet_tcp</c></tag>
<item>
<p>TCP over IPv4 (the default)</p>
</item>
<tag><c>inet_tls</c></tag>
<item>
<p>distribution over TLS/SSL</p>
</item>
<tag><c>inet6_tcp</c></tag>
<item>
<p>TCP over IPv6</p>
</item>
</taglist>
<p>For example, to start up IPv6 distributed nodes:</p>
<pre>
% <input>erl -name [email protected] -proto_dist inet6_tcp</input>
</pre>
</item>
<tag><c><![CDATA[-remsh Node]]></c></tag>
<item>
<p>Starts Erlang with a remote shell connected to <c><![CDATA[Node]]></c>.</p>
Expand Down
2 changes: 1 addition & 1 deletion erts/epmd/src/epmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -343,7 +343,7 @@ static void run_daemon(EpmdVars *g)
for (fd = 0; fd < g->max_conn ; fd++) /* close all files ... */
close(fd);
/* Syslog on linux will try to write to whatever if we dont
inform it of that the log is closed. */
inform it that the log is closed. */
closelog();

/* These shouldn't be needed but for safety... */
Expand Down
30 changes: 22 additions & 8 deletions erts/epmd/src/epmd_cli.c
Original file line number Diff line number Diff line change
Expand Up @@ -136,19 +136,33 @@ void epmd_call(EpmdVars *g,int what)
static int conn_to_epmd(EpmdVars *g)
{
struct EPMD_SOCKADDR_IN address;
size_t salen = 0;
int connect_sock;

connect_sock = socket(FAMILY, SOCK_STREAM, 0);
if (connect_sock<0)
goto error;
unsigned short sport = g->port;

#if defined(EPMD6)
SET_ADDR6(address, in6addr_loopback, sport);
salen = sizeof(struct sockaddr_in6);

connect_sock = socket(AF_INET6, SOCK_STREAM, 0);
if (connect_sock>=0) {

if (connect(connect_sock, (struct sockaddr*)&address, salen) == 0)
return connect_sock;

{ /* store port number in unsigned short */
unsigned short sport = g->port;
SET_ADDR(address, EPMD_ADDR_LOOPBACK, sport);
close(connect_sock);
}
#endif
SET_ADDR(address, htonl(INADDR_LOOPBACK), sport);
salen = sizeof(struct sockaddr_in);

if (connect(connect_sock, (struct sockaddr*)&address, sizeof address) < 0)
connect_sock = socket(AF_INET, SOCK_STREAM, 0);
if (connect_sock<0)
goto error;

if (connect(connect_sock, (struct sockaddr*)&address, salen) < 0)
goto error;

return connect_sock;

error:
Expand Down
63 changes: 43 additions & 20 deletions erts/epmd/src/epmd_int.h
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@
# ifndef WINDOWS_H_INCLUDES_WINSOCK2_H
# include <winsock2.h>
# endif
# include <ws2tcpip.h>
# include <windows.h>
# include <process.h>
#endif
Expand Down Expand Up @@ -130,6 +131,10 @@
# include <systemd/sd-daemon.h>
#endif /* HAVE_SYSTEMD_DAEMON */

#if defined(HAVE_IN6) && defined(AF_INET6) && defined(HAVE_INET_PTON)
# define EPMD6
#endif

/* ************************************************************************ */
/* Replace some functions by others by making the function name a macro */

Expand Down Expand Up @@ -183,33 +188,53 @@
/* ************************************************************************ */
/* Macros that let us use IPv6 */

#if defined(HAVE_IN6) && defined(AF_INET6) && defined(EPMD6)
#if HAVE_IN6
# if ! defined(HAVE_IN6ADDR_ANY) || ! HAVE_IN6ADDR_ANY
# if HAVE_DECL_IN6ADDR_ANY_INIT
static const struct in6_addr in6addr_any = { { IN6ADDR_ANY_INIT } };
# else
static const struct in6_addr in6addr_any =
{ { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 } } };
# endif /* HAVE_IN6ADDR_ANY_INIT */
# endif /* ! HAVE_DECL_IN6ADDR_ANY */

# if ! defined(HAVE_IN6ADDR_LOOPBACK) || ! HAVE_IN6ADDR_LOOPBACK
# if HAVE_DECL_IN6ADDR_LOOPBACK_INIT
static const struct in6_addr in6addr_loopback =
{ { IN6ADDR_LOOPBACK_INIT } };
# else
static const struct in6_addr in6addr_loopback =
{ { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1 } } };
# endif /* HAVE_IN6ADDR_LOOPBACK_INIT */
# endif /* ! HAVE_DECL_IN6ADDR_LOOPBACK */
#endif /* HAVE_IN6 */

#define IS_ADDR_LOOPBACK(addr) ((addr).s_addr == htonl(INADDR_LOOPBACK))

#if defined(EPMD6)

#define EPMD_SOCKADDR_IN sockaddr_in6
#define EPMD_IN_ADDR in6_addr
#define EPMD_S_ADDR s6_addr
#define EPMD_ADDR_LOOPBACK in6addr_loopback.s6_addr
#define EPMD_ADDR_ANY in6addr_any.s6_addr
#define EPMD_SOCKADDR_IN sockaddr_storage
#define FAMILY AF_INET6

#define SET_ADDR(dst, addr, port) do { \
memset((char*)&(dst), 0, sizeof(dst)); \
memcpy((char*)&(dst).sin6_addr.s6_addr, (char*)&(addr), 16); \
(dst).sin6_family = AF_INET6; \
(dst).sin6_flowinfo = 0; \
(dst).sin6_port = htons(port); \
#define SET_ADDR6(dst, addr, port) do { \
struct sockaddr_in6 *sa = (struct sockaddr_in6 *)&(dst); \
memset(sa, 0, sizeof(dst)); \
sa->sin6_family = AF_INET6; \
sa->sin6_addr = (addr); \
sa->sin6_port = htons(port); \
} while(0)

#define IS_ADDR_LOOPBACK(addr) \
(memcmp((addr).s6_addr, in6addr_loopback.s6_addr, 16) == 0)
#define SET_ADDR(dst, addr, port) do { \
struct sockaddr_in *sa = (struct sockaddr_in *)&(dst); \
memset(sa, 0, sizeof(dst)); \
sa->sin_family = AF_INET; \
sa->sin_addr.s_addr = (addr); \
sa->sin_port = htons(port); \
} while(0)

#else /* Not IP v6 */

#define EPMD_SOCKADDR_IN sockaddr_in
#define EPMD_IN_ADDR in_addr
#define EPMD_S_ADDR s_addr
#define EPMD_ADDR_LOOPBACK htonl(INADDR_LOOPBACK)
#define EPMD_ADDR_ANY htonl(INADDR_ANY)
#define FAMILY AF_INET

#define SET_ADDR(dst, addr, port) do { \
Expand All @@ -219,8 +244,6 @@
(dst).sin_port = htons(port); \
} while(0)

#define IS_ADDR_LOOPBACK(addr) ((addr).s_addr == htonl(INADDR_LOOPBACK))

#endif /* Not IP v6 */

/* ************************************************************************ */
Expand Down
Loading

0 comments on commit 75bc5be

Please sign in to comment.