Pregunta TCP Hole Punch (NAT Traversal) ¿Biblioteca o algo así?


Quiero hacer TCP Perforación de taladro (NAT Traversal) en C #. Se puede hacer con un servidor de encuentro si es necesario. encontré http://sharpstunt.codeplex.com/ pero no puede hacer que esto funcione. Idealmente, necesito algún método que proporcione un Número de puerto (int) como parámetro que después de una llamada a este método está disponible ("Reenvío de puerto") en el NAT. También estaría bien si el método simplemente devuelve un número de puerto que luego está disponible en el NAT. Alguien ha hecho esto en C #? ¿Me puede dar ejemplos de trabajo para sharpstunt o algo más?


32
2018-03-14 19:39


origen


Respuestas:


En cada escenario de red, la perforación de orificios TCP funciona de manera similar a la perforación con orificios UDP. Por ejemplo, si dos pares A y B están detrás de diferentes NAT, el primer paquete SYN de cada par enviado al otro par abre un agujero asociado con su dirección pública en su respectivo NAT. Si el primer paquete SYN de A llega a B, NAT antes de que el primer paquete SYN de B llegue a la NAT de B, la NAT de B considera el paquete SYN de A no solicitado y lo descarta. Sin embargo, posteriormente, el primer paquete SYN de B puede viajar a través de la NAT de A con éxito porque la NAT de A reconoce la dirección pública de B como el destino de la sesión saliente que A ha iniciado.

Entonces sí. Es posible perforar el agujero TCP. No veo por qué alguien pensaría lo contrario.

Además, ¿no podrías crear este tipo de comportamiento de forma manual? No necesita depender de ningún protocolo específico, siempre y cuando los pasos sean los mismos para recopilar toda la información requerida.

En general, la perforación de agujeros TCP (3.2.1) procede de la siguiente manera:

Clientes: A, B Servidor: S

• A usa su conexión con S para pedirle a S una conexión con B. • S responde a A con las direcciones privada y pública de B, y simultáneamente envía direcciones de A a B.

• A y B hacen asincrónicamente conexión saliente en- tentado (enviar paquetes SYN) al público de cada uno y direcciones privadas, desde el mismo puerto que usaron para registrarse con S. Al mismo tiempo, escuchan La conexión TCP entrante intenta en su TCP local puertos.

• A y B esperan una respuesta SYN-ACK a su salida pasando paquetes SYN, o una solicitud de conexión entrante (Paquete SYN). Si una conexión falla, el par puede volver a intentarlo hasta un período máximo de tiempo de espera.

• Una vez que se ha completado el proceso de enlace de tres vías, los pares se autentican entre sí. Si la autenticación falla, los pares cierran esa conexión y esperan hasta otra conexión se autentica con éxito. los se usará la primera conexión autenticada con éxito para transferir datos TCP

(Sé que esto no es una gran respuesta, pero no había espacio suficiente para un comentario).


17
2018-06-04 19:52



Parece que podrías confundir TCP y UDP. TCP es un protocolo orientado a la conexión, fácil de entender por firewalls y enrutadores, y requiere un iniciador (cliente) y un oyente (servidor). Si tanto el cliente como el servidor están detrás de firewalls o NAT, no se puede abrir un agujero sin que ambos se conecten a algún servidor proxy (que no tiene cortafuegos). El problema con esto es que entonces el proxy sería responsable de transmitir todo su tráfico.

A partir de su pregunta, parece que está más interesado en la perforación de agujeros UDP, que explota la grasa de que el UDP es apátrida y no está orientado a la conexión. Por lo tanto, la mayoría de los servidores de seguridad de seguimiento de estado harán una "mejor estimación" sobre el flujo de datos UDP, y supondrán que el tráfico que sale de un puerto determinado recibirá respuestas en el mismo puerto y las redirigirá automáticamente. Si, usando algunos medios fuera del canal (como un servidor TCP que simplemente transfiere direcciones y no datos), ambos pares pueden estar transmitiendo datos entre sí en los mismos puertos, sus respectivos firewalls / enrutadores NAT abrirán agujeros permitiendo el tráfico en.

En cuanto a cómo hacerlo, todo depende de cómo va a obtener la dirección IP de los pares entre sí. Una vez que lo tenga, simplemente comience a transmitir paquetes UDP en un puerto acordado, y espere una respuesta.


2
2017-07-08 18:09



Armamos una biblioteca llamada IceLink eso hace la transmisión P2P usando ICE / STUN / TURN con cruce de NAT completo. El taladrado de orificios basado en STUN funciona para la mayoría de los enrutadores para establecer una conexión directa entre pares, y para los enrutadores "malos", la conexión vuelve a un relé basado en TURN.


2
2017-12-04 23:06



La pregunta es bastante antigua, pero para cualquiera que busque una solución, debe echarle un vistazo al Proyecto Open.NAT ¡es realmente fácil de usar y funciona con UPNP y PMP NATs!

Digamos que desea reenviar el puerto 1700 al puerto local 1600, todo lo que tiene que hacer es:

var discoverer = new NatDiscoverer();
var device = await discoverer.DiscoverDeviceAsync();
await device.CreatePortMapAsync(new Mapping(Protocol.Tcp, 1600, 1700, "The mapping name"));

También puede listar todas las asignaciones existentes, para que pueda validar que su puerto no está siendo utilizado.

var sb = new StringBuilder();
var ip = await device.GetExternalIPAsync();

sb.AppendFormat("\nAdded mapping: {0}:1700 -> 127.0.0.1:1600\n", ip);
sb.AppendFormat("\n+------+-------------------------------+--------------------------------+------------------------------------+-------------------------+");
sb.AppendFormat("\n| PROT | PUBLIC (Reacheable)           | PRIVATE (Your computer)        | Descriptopn                        |                         |");
sb.AppendFormat("\n+------+----------------------+--------+-----------------------+--------+------------------------------------+-------------------------+");
sb.AppendFormat("\n|      | IP Address           | Port   | IP Address            | Port   |                                    | Expires                 |");
sb.AppendFormat("\n+------+----------------------+--------+-----------------------+--------+------------------------------------+-------------------------+");
foreach (var mapping in await device.GetAllMappingsAsync())
{
    sb.AppendFormat("\n|  {5} | {0,-20} | {1,6} | {2,-21} | {3,6} | {4,-35}|{6,25}|",
        ip, mapping.PublicPort, mapping.PrivateIP, mapping.PrivatePort, mapping.Description, mapping.Protocol == Protocol.Tcp ? "TCP" : "UDP", mapping.Expiration.ToLocalTime());
}
sb.AppendFormat("\n+------+----------------------+--------+-----------------------+--------+------------------------------------+-------------------------+");
Console.WriteLine(sb.ToString());

También hay una publicación de blog sobre NAT Traversal en MSDN: https://blogs.msdn.microsoft.com/ncl/2009/07/27/end-to-end-connectivity-with-nat-traversal/


2
2018-05-18 18:28



http://sipsorcery.codeplex.com tiene un servidor de aturdimiento activo.

SipSorcery.core -> SipSorcery.Net -> Aturdir


1
2018-04-26 11:00



No estoy familiarizado con su tema, pero conozco un P2PVPN de código abierto, que usa una lib para hacer NAT. Puede consultarlo aquí (www.SocialVPN.org).

Buena suerte.


0
2018-04-23 08:02