Open kdeme opened 3 years ago
To make clear, in the current code with current options, the only real viable options are:
Systems not behind NAT:
--nat:extip:x.x.x.x
Systems behind NAT:
--nat:extip:x.x.x.x
and make manually configure port forwarding in the router/gateway.upnp
or pmp
) and make sure this functionality is enabled in your router. Port forwarding and external ip discovery will happen automated (but more issues might occur because of this). Thinking about it further, the any
option (defaulted), should basically allow for any of the two cases to work automatically. However, not guaranteed of course and issues may arise. It would be more important to have proper INF
and WRN
logs for this and educate the users into these message (in the book).
This would mean still using the upnp/pmp solution default & also discv5 solution. Basically what LH is doing.
(And perhaps we can also implement the none
solution from above as backup).
Thinking about it further, the any option (defaulted), should basically allow for any of the two cases to work automatically. However, not guaranteed of course and issues may arise. It would be more important to have proper INF and WRN logs for this and educate the users into these message (in the book). This would mean still using the upnp/pmp solution default & also discv5 solution. Basically what LH is doing.
As discussed offline, I think this is the cleanest approach.
I think before starting NAT mechanism we should check our interfaces and routing table using chronos
utilities. This will allow us to detect situation when we already have public IP address and we do not need to start NAT mechanism.
https://github.com/status-im/nim-chronos/blob/master/tests/testnet.nim#L477-L482
Using getBestRoute
with some globally available IP address will reveal you interface's address which will be used to connect to this IP address. If this IP address is globally routable you can use it as "extip".
The only problem is that currently chronos
is missing primitive to check if specific IP is actually global routable IP address.
Using
getBestRoute
with some globally available IP address will reveal you interface's address which will be used to connect to this IP address. If this IP address is globally routable you can use it as "extip".
Great, this is what I meant with:
* the routable interface could be searched for and its IP could be used, but this would not be necessary.
I wasn't aware that there was a getBestRoute
call available in chronos already. It does seems to require sending an actual message, is that correct? Is there a version that just checks routable interface?
@kdeme this call do not send any messages, it just query OS for the BEST route. Because there could be many routable interfaces actually...
The bulk of this feature is being implemented here: https://github.com/status-im/nim-eth/pull/323
The current (new) logic is as follows:
any
:
bindIP
) is given, and this IP is public, use this IP in the ENR (advertised IP). (not sure if we should still help the user here and check if this is also best route IP, or allow for more exotic uses).upnp
: Try UPnP to discover IP and do port mapping. If it fails, no IP is set, warning is given.pmp
: Try NAT-PMP to discover IP and do port mapping. If it fails, no IP is set, warning is given.none
:
bindIP
) is given, and this IP is public, use this IP in the ENR (advertised IP). (not sure if we should still help the user here and check if this is also best route IP, or allow for more exotic uses). Else warn that --none
option should not be used.--none
option should not be used.extip:<IP address>
: Use this IP in ENR. Nothing else is done. This will allow for private IP usage also. (We use this in testing)Additionally, external IP discovery should be added in discv5 protocol (and allowed to be disabled). This will help with dynamic IP that get changed and also in the case that external IP can not be found correctly (e.g. Container / VM usages or cases where the best route IP findings would go wrong?).
Now, some questions:
--nat:...
options stem from geth. Are these clear enough for the user? I think they are not very self explanatory and it might be rather difficult to understand what to use here. On the other hand, the default is any
and that should be fine for the typical user. But we could decide to change to more individual based options however too, e.g. with the same default results (and keep the current options also available for a certain period for backwards compatibility)Some different use cases:
I'm leaving out IPv6 cases for now.
From my experience PMP works better than UPNP because PMP can give you other external port in case the requested one is already taken. But seems nimbus is trying UPNP first and errors out without fallback to PMP.
Current default is to use upnp / nat pmp to discover external ip and to configure the port forwarding ( =mapping). This is not useful for systems not behind NAT as thus not a great default for those configurations. Additionally, we might no want to recommend upnp first option either for those behind NAT?
Discoveryv5 can help figuring out the external IP when https://github.com/status-im/nim-eth/issues/207 gets implemented. When the user is behind NAT, it would still require for manual port mapping or to be used in combination with upnp/natpmp
Regarding the
--nat
option:--nat:extip:
option can still be used for those that want to hard set the ip and not rely on peers.none
option could be implemented such that the routable interface is discovered and its ip address is used (if not local address).any
would be a mix, and could thus e.g. rely on upnp + discv5 or finding of routable interface + discv5.Default could still be
any
option.Defaults:
Other clients: