Обход маршрутизатора с использованием сервера для установления соединения - PullRequest
1 голос
/ 16 апреля 2011

Я хотел бы создать простую программу чата на Java, которая могла бы работать на основе p2p.Использование публичного сервера только для инициирования соединения.Но я даже не уверен, что это возможно.

Я успешно реализовал решение для чата на Java, которое работает, если хотя бы один компьютер перенаправил нужные порты.Мне также удалось использовать внешний сервер вместо того, чтобы иметь перенаправленные порты на стороне клиента.

Так что я, хотя, было бы даже возможно, каким-то образом использовать публичный сервер для инициирования соединения, а затем отправлять данные прямо между клиентамизагрузка с сервера?

Я не очень хорошо знаю, как работают маршрутизаторы, но я ожидаю, что при вызове общедоступного сервера с внутреннего IP-адреса маршрутизатор запоминает этот вызов и входящий ответ с этого общедоступного IP-адреса, чем отправляет на вашПК.Поэтому я подумал, может быть, если первый клиент подключился к серверу, а сервер передал информацию второму клиенту, может быть, они могли бы как-то напрямую связаться?Если правило в роутере было установлено сервером?

Надеюсь, я объяснил это ясно.Если нет, пожалуйста, извините.Я даже не знаю, как именно это можно сделать, я просто хочу знать, есть ли что-то правильное в моей концепции, и мне нужно больше учиться, чтобы начать работать.Спасибо.

Ответы [ 3 ]

5 голосов
/ 16 апреля 2011

Я думаю, TeleHash - это новый проект, который может делать такие вещи.Я узнал об этом только недавно, поэтому не знаю много об этом.

Я сделал этот ответ в вики сообщества, чтобы другие могли обновить его, чтобы объяснить, как TeleHash может использоваться для этого.

4 голосов
/ 16 апреля 2011

Это обширная тема, ищите дырокол (для TCP: http://en.wikipedia.org/wiki/TCP_hole_punching)

0 голосов
/ 16 апреля 2011

Редактировать: После комментариев (и прочтения связанных страниц) я должен отступить от своего совета. Я не удаляю его, для хорошей графики, но изменил последнюю часть.


Если я правильно понимаю, у вас есть два клиента, оба за брандмауэром NAT, который разрешает исходящие соединения, но не переадресовывает входящие соединения, если специально не настроен для этого (так как они не знают, для каких локальных хостов это происходит) сУЖДЕНО).

В принципе, TCP-соединение в течение всего времени своего существования всегда соединяет одни и те же два IP-адреса и номера портов по этим адресам (например, у нас есть четыре числа, которые остаются постоянными). В случае NAT у вас фактически есть два соединения, но это не видно ни на клиентском компьютере A (ни на сервере S):

Client A  -------(LAN)------ NAT B      ------ (Internet) -------- Server S
  IP A                   IP B1 | IP B2                               IP S
  Port a                       | Port b                              Port s

Пакеты TCP имеют адреса [A: a / S: s] (или [S: s / A: a]) в локальной сети и [B2: b / S: s] (или [S: s / B2: b]) адреса в интернет-части. Соединение идентифицируется этим четырехкратным [IP: порт / IP: порт], поэтому, если вы попытаетесь изменить хотя бы одно из четырех чисел, это должно быть новое соединение (или пакет будет отброшен).

Итак, если вы впервые общаетесь с вашим сервером, вы не можете продолжать общение с другим клиентом по тому же соединению, если только сервер не пересылает содержимое.

То же самое на самом деле имеет место для пакетов UDP, с той разницей, что нет никаких соединений, и NAT должен быть умным и угадывать, какой пакет является ответом на какой-либо другой пакет, и, как таковой, направить его вправо направление.

Как отмечается в комментариях и других ответах, здесь можно обмануть NAT: сначала мы отправляем UDP-пакет другому клиенту, который будет отброшен NAT там. Но затем другой клиент отправляет ответный пакет, который не является реальным ответом на исходящий пакет (поскольку этот пакет никогда не получался из-за NAT других клиентов), но IP-адреса и номера портов совпадают, он все равно будет пропущен. Это может усложниться, если NAT также преобразует номера портов.

Для TCP он может работать аналогично, если оба NAT на самом деле не поддерживают открытое соединение, а просто пересылают (изменяют) пакеты, когда ранее был отправлен SYN. Это еще сложнее, поскольку здесь также должны совпадать порядковые номера TCP.

...