예제 #1
0
        public void Initialize()
        {
            Logger.Info("Initializing networking");

            while (true)
            {
                try {
                    _stunQuery = null;
                    CheckNatType();

                    if (_stunQuery != null)
                    {
                        break;
                    }
                } catch (Exception e) {
                    Logger.Error("Unable to initialize networking! Retrying", e);
                    Thread.Sleep(5000);
                }
            }

            if (_stunQuery.NetworkType == StunNetworkType.UdpBlocked)
            {
                Logger.Warn("First NAT detectiont return that UDP is fully blocked. Trying second time with timeout of 5 seconds ...");
                Thread.Sleep(5000);
                Initialize();
                return;
            }

            _remoteEp = _stunQuery.PublicEndPoint;
            var internalPort = ((IPEndPoint)_socket.LocalEndPoint).Port;

            Logger.Debug($"P2P connections are listen as external {_stunQuery.PublicEndPoint.Address}:{_stunQuery.PublicEndPoint.Port}, local bind is {_bindEp.Address}:{internalPort}");
            Logger.Info($"Bound local socket at {(IPEndPoint) _socket.LocalEndPoint}");

            _portMapping = new Mapping(Protocol.Udp, internalPort, _stunQuery.PublicEndPoint.Port, $"RHMS Internal Peer {_connectionManager.GetSelfHostId()} Map");

            Monitor.Enter(_natUpnpCreateLocker);
            Task.Run(async() => {
                try {
                    var discoverer = new NatDiscoverer();
                    var cts        = new CancellationTokenSource(10000);
                    var device     = await discoverer.DiscoverDeviceAsync(PortMapper.Upnp, cts);
                    await device.CreatePortMapAsync(_portMapping);

                    Logger.Info($"Created UPnP mapping {_portMapping}");
                } catch (Exception e) {
                    Logger.Error("Unable to create UPnP mapping!", e);
                }
            }).Wait();
            Monitor.Exit(_natUpnpCreateLocker);

            NetworkStartAcceptingData();
        }
예제 #2
0
        private bool PerformNatQueryOn(string host, int port)
        {
            Logger.Debug($"Performing STUN query to {host}:{port}");
            _stunQuery = StunQuery.Perform(_socket, host, port);
            if (_stunQuery == null || _stunQuery.NetworkType == StunNetworkType.CommunicationError)
            {
                _stunQuery = null;
                Logger.Debug($"STUN query to {host}:{port} failed with communication error");
                return(false);
            }

            return(true);
        }