Supporting a port number in spawn/4

classic Classic list List threaded Threaded
6 messages Options
Reply | Threaded
Open this post in threaded view
|

Supporting a port number in spawn/4

Amit K
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)

Thanks!
Amit

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Supporting a port number in spawn/4

Grzegorz Junka


On 21/10/2019 21:25, Amit K wrote:
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)


Hi Amit,

There is also another option, run any communication between nodes via IP tunnels. There are some tools to automate that. They are mostly used between docker containers or pods but it's just a detail, equally well they can support a microarchitecture build on Erlang nodes.

Regards
Greg


_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Supporting a port number in spawn/4

Amit K
Hi Greg,

Thank you for your feedback!
In general, I think it makes sense to have a solution for this that's built in to OTP and not have to use an external proxy method. 
Going more along the route of what you suggest, a sensible alternative would be for epmd.exe to be able to accept TLS settings like the Erlang node (erl.exe) does, and then communication with it will also be protected by TLS. a quick look at the code makes me  guess that the reason that was not done originally is that epmd is a small & separate utility written in C and therefore it doesn't have the "crypto" framework like the other OTP parts do.

Regards,
Amit



On Tue, Oct 22, 2019 at 10:54 AM Grzegorz Junka <[hidden email]> wrote:


On 21/10/2019 21:25, Amit K wrote:
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)


Hi Amit,

There is also another option, run any communication between nodes via IP tunnels. There are some tools to automate that. They are mostly used between docker containers or pods but it's just a detail, equally well they can support a microarchitecture build on Erlang nodes.

Regards
Greg

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Supporting a port number in spawn/4

Lukas Larsson-8


On Tue, Oct 22, 2019 at 1:02 PM Amit K <[hidden email]> wrote:
Hi Greg,

Thank you for your feedback!
In general, I think it makes sense to have a solution for this that's built in to OTP and not have to use an external proxy method. 
Going more along the route of what you suggest, a sensible alternative would be for epmd.exe to be able to accept TLS settings like the Erlang node (erl.exe) does, and then communication with it will also be protected by TLS. a quick look at the code makes me  guess that the reason that was not done originally is that epmd is a small & separate utility written in C and therefore it doesn't have the "crypto" framework like the other OTP parts do.

I'm kind of curious about what type of attacks you are trying to protect against? You mention "man in the middle", however, I cannot see how someone could exploit that to do anything but disrupt the distributed erlang connections. Though that could only be a lack of imagination on my part, and when it comes to security we must be extra careful.

Lukas
 

Regards,
Amit



On Tue, Oct 22, 2019 at 10:54 AM Grzegorz Junka <[hidden email]> wrote:


On 21/10/2019 21:25, Amit K wrote:
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)


Hi Amit,

There is also another option, run any communication between nodes via IP tunnels. There are some tools to automate that. They are mostly used between docker containers or pods but it's just a detail, equally well they can support a microarchitecture build on Erlang nodes.

Regards
Greg

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Supporting a port number in spawn/4

Amit K
Hi Lukas,

It's a great question! 
And actually, choosing between disabling epmd completely and protecting communication via TLS, will have somewhat different security benefits. 

1. Protecting epmd communication via TLS - This only protects us from an attacker that wants to perform epmd impersonation, because TLS here is authenticating only the server node to the client node. 
Then perhaps if we have two Erlang nodes on the same machine, let's say Node1 and Node2, an attacker can make the client node connect to Node2 instead of Node1 by returning the wrong port by a simple manipulation of the plain epmd traffic, and in that way expose sensitive data to the client node, which exists in Node2 but not in Node1. Maybe it's a bit far fetched but from my limited knowledge it looks like a possible attack scenario. 
Another thing that the encryption is good for here is probably in preventing a covert channel.  

2. Disabling epmd completely - This approach eliminates a lot more attack vectors actually. 
Just as one simple example, assume for a moment that we have a buffer overflow bug in epmd, then using this approach you will not be affected by it. By completely disabling an unnecessary service (if it's really unnecessary of course, in some situations I assume epmd is very much required!) the attack surface reduces much more so it's difficult to list in detail everything we'll be protecting against. 
Nevertheless, we all know that it's a good security practice to disable unrequired services whenever you can :) and especially ones that listen to requests from the outside world.

Regards,
Amit

On Tue, Oct 22, 2019 at 2:49 PM Lukas Larsson <[hidden email]> wrote:


On Tue, Oct 22, 2019 at 1:02 PM Amit K <[hidden email]> wrote:
Hi Greg,

Thank you for your feedback!
In general, I think it makes sense to have a solution for this that's built in to OTP and not have to use an external proxy method. 
Going more along the route of what you suggest, a sensible alternative would be for epmd.exe to be able to accept TLS settings like the Erlang node (erl.exe) does, and then communication with it will also be protected by TLS. a quick look at the code makes me  guess that the reason that was not done originally is that epmd is a small & separate utility written in C and therefore it doesn't have the "crypto" framework like the other OTP parts do.

I'm kind of curious about what type of attacks you are trying to protect against? You mention "man in the middle", however, I cannot see how someone could exploit that to do anything but disrupt the distributed erlang connections. Though that could only be a lack of imagination on my part, and when it comes to security we must be extra careful.

Lukas
 

Regards,
Amit



On Tue, Oct 22, 2019 at 10:54 AM Grzegorz Junka <[hidden email]> wrote:


On 21/10/2019 21:25, Amit K wrote:
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)


Hi Amit,

There is also another option, run any communication between nodes via IP tunnels. There are some tools to automate that. They are mostly used between docker containers or pods but it's just a detail, equally well they can support a microarchitecture build on Erlang nodes.

Regards
Greg

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
Reply | Threaded
Open this post in threaded view
|

Re: Supporting a port number in spawn/4

Oleg Tarasenko
Hey Amit,

Actually I am maintaining a small project which is dedicated to the topic above: 

See also the article regarding running it in docker:

Hopefully it could be interesting for you as well,
Oleg

On Tue, Oct 22, 2019 at 2:11 PM Amit K <[hidden email]> wrote:
Hi Lukas,

It's a great question! 
And actually, choosing between disabling epmd completely and protecting communication via TLS, will have somewhat different security benefits. 

1. Protecting epmd communication via TLS - This only protects us from an attacker that wants to perform epmd impersonation, because TLS here is authenticating only the server node to the client node. 
Then perhaps if we have two Erlang nodes on the same machine, let's say Node1 and Node2, an attacker can make the client node connect to Node2 instead of Node1 by returning the wrong port by a simple manipulation of the plain epmd traffic, and in that way expose sensitive data to the client node, which exists in Node2 but not in Node1. Maybe it's a bit far fetched but from my limited knowledge it looks like a possible attack scenario. 
Another thing that the encryption is good for here is probably in preventing a covert channel.  

2. Disabling epmd completely - This approach eliminates a lot more attack vectors actually. 
Just as one simple example, assume for a moment that we have a buffer overflow bug in epmd, then using this approach you will not be affected by it. By completely disabling an unnecessary service (if it's really unnecessary of course, in some situations I assume epmd is very much required!) the attack surface reduces much more so it's difficult to list in detail everything we'll be protecting against. 
Nevertheless, we all know that it's a good security practice to disable unrequired services whenever you can :) and especially ones that listen to requests from the outside world.

Regards,
Amit

On Tue, Oct 22, 2019 at 2:49 PM Lukas Larsson <[hidden email]> wrote:


On Tue, Oct 22, 2019 at 1:02 PM Amit K <[hidden email]> wrote:
Hi Greg,

Thank you for your feedback!
In general, I think it makes sense to have a solution for this that's built in to OTP and not have to use an external proxy method. 
Going more along the route of what you suggest, a sensible alternative would be for epmd.exe to be able to accept TLS settings like the Erlang node (erl.exe) does, and then communication with it will also be protected by TLS. a quick look at the code makes me  guess that the reason that was not done originally is that epmd is a small & separate utility written in C and therefore it doesn't have the "crypto" framework like the other OTP parts do.

I'm kind of curious about what type of attacks you are trying to protect against? You mention "man in the middle", however, I cannot see how someone could exploit that to do anything but disrupt the distributed erlang connections. Though that could only be a lack of imagination on my part, and when it comes to security we must be extra careful.

Lukas
 

Regards,
Amit



On Tue, Oct 22, 2019 at 10:54 AM Grzegorz Junka <[hidden email]> wrote:


On 21/10/2019 21:25, Amit K wrote:
Hi all,

I am very new to Erlang, am considering to use it in a project and I have some security concerns. 
I can see it's quite easy to configure TLS for the node-to-node communication, but making the name-to-port resolution service (epmd) secure seem a bit too complex to me, such as the one suggested here: https://www.erlang-solutions.com/blog/erlang-and-elixir-distribution-without-epmd.html

So I was thinking, seeing that there are already options to:
1. Start a distributed node without epmd (-start_epmd false
2. Limit a node's port numbers to a specific range (via inet_dist_listen_min & inet_dist_listen_max).

Wouldn't it be nice if we could also specify a predefined port to spawn/4, to complete that picture? That is allow spawn to look like:
spawn("Name@Host:Port", Mod, Func, ArgList). 
Then when spawn sees that a port was provided, it can completely skip the "epmd resolution" part and proceed with connecting to the target node via the provided port. 
Note: I realize that the "Name" becomes slightly redundant when the Port is explicit. However this can still be useful - it would be good if the implementation will also verify that the port belongs to the provided name at the receiving side, so that a node will not accidentally process a message that wasn't meant for it.

Again, I'm a complete newbie to Erlang in general, so I may be missing something essential here :) But I would love to know what that is, if that's the case, or hear your thoughts in general otherwise :)


Hi Amit,

There is also another option, run any communication between nodes via IP tunnels. There are some tools to automate that. They are mostly used between docker containers or pods but it's just a detail, equally well they can support a microarchitecture build on Erlang nodes.

Regards
Greg

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions
_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions

_______________________________________________
erlang-questions mailing list
[hidden email]
http://erlang.org/mailman/listinfo/erlang-questions