web-dev-qa-db-fra.com

Bouclage vers l'adresse IP publique transmise à partir du réseau local - Épingle à cheveux NAT

Il s'agit d'une Question canonique à propos de Hairpin NAT (Loopback NAT).

La forme générique de cette question est:

Nous avons un réseau avec des clients, un serveur et un NAT routeur. Il y a une redirection de port sur le routeur vers le serveur, donc certains de ses services sont disponibles en externe. Nous avons DNS pointant vers l'extérieur IP. Les clients du réseau local ne parviennent pas à se connecter, mais le travail externe.

  • Pourquoi cela échoue-t-il?
  • Comment puis-je créer un schéma de nommage unifié (noms DNS qui fonctionnent à la fois localement et extérieurement)?

Cette question a des réponses fusionnées à partir de plusieurs autres questions. À l'origine, ils faisaient référence à FreeBSD, D-Link, Microtik et à d'autres équipements. Cependant, ils essaient tous de résoudre le même problème.

46
adopilot

Ce que vous recherchez s'appelle "NAT en épingle à cheveux". Les demandes provenant de l'interface interne pour une adresse IP attribuée à l'interface externe doivent être NATtées comme si elles provenaient de l'interface externe.

Je n'ai aucune connaissance de FreeBSD, mais la lecture du manuel "pf" pour OpenBSD ( http://www.openbsd.org/faq/pf/rdr.html ) les solutions proposées de DNS à horizon partagé, utilisant un réseau DMZ, ou TCP me porte à croire que "pf" ne prend pas en charge le NAT en épingle à cheveux).

Je chercherais à suivre la voie du DNS à horizon divisé et à ne pas utiliser les adresses IP dans les URL en interne, mais plutôt à utiliser des noms.

16
Evan Anderson

Étant donné que cela a été élevé pour être la question canonique sur le NAT en épingle à cheveux, j'ai pensé qu'il devrait probablement y avoir une réponse qui était plus généralement valide que celle actuellement acceptée, qui (bien qu'excellente) se rapporte spécifiquement à FreeBSD.

Cette question s'applique aux services fournis par les serveurs sur les réseaux IPv4 adressés par RFC1918, qui sont mis à la disposition des utilisateurs externes en introduisant la destination NAT (DNAT) sur la passerelle. Les utilisateurs internes essaient ensuite d'accéder à ces services via l'adresse externe. Leur paquet sort du client vers le périphérique de passerelle, qui réécrit l'adresse de destination et la réinjecte immédiatement dans le réseau interne. C'est ce retournement brutal du paquet à la passerelle qui donne lieu à la nom NAT en épingle à cheveux , par analogie avec le tour en épingle à cheveux .

Le problème survient lorsque le périphérique passerelle réécrit l'adresse de destination, mais pas l'adresse source. Le serveur reçoit alors un paquet avec une adresse de destination interne (la sienne) et une adresse source interne (celle du client); il sait qu'il peut répondre directement à une telle adresse, il le fait donc. Comme cette réponse est directe, elle ne passe pas par la passerelle, qui n'a donc jamais la possibilité d'équilibrer l'effet de la destination entrante NAT sur le paquet initial en réécrivant l'adresse source du retour) paquet.

Le client envoie donc un paquet à une adresse IP externe, mais obtient une réponse d'une adresse IP interne. Il n'a aucune idée que les deux paquets font partie de la même conversation, donc aucune conversation ne se produit.

La solution est que pour les paquets qui nécessitent une telle destination NAT, et qui atteignent la passerelle depuis le réseau interne, pour effectuer également la source NAT (SNAT) sur le paquet entrant, généralement en réécrivant l'adresse source pour être celle de la passerelle. Le serveur pense alors que le client est la passerelle elle-même et y répond directement. Cela donne à la passerelle une chance d'équilibrer les effets de DNAT et SNAT sur le paquet entrant en réécrivant les adresses source et de destination sur le paquet de retour.

Le client pense qu'il parle à un serveur externe. Le serveur pense qu'il parle au périphérique passerelle. Toutes les parties sont heureuses. Un diagramme peut être utile à ce stade:

enter image description here

Certains périphériques de passerelle grand public sont suffisamment brillants pour reconnaître les paquets pour lesquels la deuxième étape NAT est nécessaire, et ceux-ci fonctionneront probablement prêts à l'emploi dans une épingle à cheveux NAT. D'autres ne le sont pas et ne le seront pas, et il est peu probable qu'ils puissent fonctionner. Une discussion sur les périphériques grand public qui est hors sujet pour Server Fault.

On peut généralement dire aux appareils de mise en réseau appropriés de fonctionner, mais - parce qu'ils n'ont pas pour tâche de deviner leurs administrateurs - ils doivent le leur dire. Linux utilise iptables pour faire le DNAT ainsi:

iptables -t nat -A PREROUTING  -p tcp --dport 80 -j DNAT --to-destination 192.168.3.11

qui permettra à DNAT simple pour le port HTTP, à un serveur interne sur 192.168.3.11. Mais pour activer le NAT en épingle à cheveux, il faudrait également une règle telle que:

iptables -t nat -A POSTROUTING -d 192.168.3.11 -p tcp --dport 80 -j MASQUERADE

Notez que ces règles doivent être au bon endroit dans les chaînes appropriées pour fonctionner correctement, et selon les paramètres de la chaîne filter, des règles supplémentaires peuvent être nécessaires pour permettre au trafic NATted de circuler. Toutes ces discussions sortent du cadre de cette réponse.

Mais comme d'autres l'ont dit, l'activation correcte de l'épingle à cheveux NAT n'est pas la meilleure façon de gérer le problème. Le mieux est DNS à horizon partagé , où votre organisation sert des réponses différentes pour la recherche d'origine en fonction de l'emplacement du client demandeur, soit en ayant des serveurs physiques différents pour les utilisateurs internes vs externes, soit en configurant le serveur DNS pour répondre différemment selon le adresse du client demandeur.

49
MadHatter

Le problème ici est que votre routeur ne fait pas NAT l'adresse de votre client interne. Ainsi, la prise de contact TCP échoue.

Supposons que les adresses IP suivantes

  • Client: 192.168.1.3
  • Serveur: 192.168.1.2
  • Routeur interne: 192.168.1
  • Routeur externe: 123.123.123.1

Voici ce qui se passe:

  1. Le client (192.168.1.3) envoie TCP-SYN à votre IP externe, port 80 (123.123.123.1:80)
  2. Le routeur voit la règle de redirection de port et transfère le paquet au serveur (192.168.1.2:80) sans changer l'adresse IP source (192.168.1.3)
  3. Le client attend un SYN-ACK de l'IP externe
  4. Le serveur renvoie directement sa réponse au client, car il se trouve sur le même sous-réseau. Il n'envoie pas le paquet au routeur, ce qui inverserait le NAT.
  5. Le client reçoit un SYN-ACK de 192.168.1.2 au lieu de 123.123.123.1. Et le jette.
  6. Le client attend toujours un SYN-ACK de 123.123.123.1 et expire.
9
PEra

Pourquoi ne pas utiliser le DNS à horizon divisé au lieu de coder en dur les adresses IP partout? Vous auriez votre domaine externe pointé vers 217.x.x.x à l'extérieur, puis 192.x.x.x à l'intérieur.

4
Ryaner

S'il s'agit d'un routeur D-Link d'origine (c'est-à-dire pas de la version Rev. D/Firmware 1.00VG de Virgin Media), vous devriez pouvoir ajuster les paramètres pour contourner ce problème. (Cependant, je suis d'accord avec la suggestion de DD-WRT de l'affiche précédente pour de nombreuses autres raisons!)

  1. Connectez-vous à l'interface Web du routeur
  2. Cliquez sur l'onglet Avancé en haut
  3. Cliquez sur l'onglet Paramètres du pare-feu à gauche
  4. Cliquez sur le bouton radio Indépendant du point final sous Filtrage des points finaux TCP , comme illustré dans la capture d'écran ci-dessous (ou voir le émulateur de routeur sur le site Web de D-Link)
  5. Sauvegarder les modifications; vous avez terminé

D-Link router web UI screenshot

Cette capture d'écran est issue du modèle Rev. C; le vôtre peut être légèrement différent.

2
David

A récemment répondu à une question similaire: Cisco static NAT ne fonctionne pas du côté LAN et vient de réaliser qu'il s'agit d'une question canonique. Permettez-moi donc de résumer la solution ici.

Tout d'abord: oubliez NAT (si vous le pouvez) - la question n'est pas du tout de configurer NAT. Il s'agit d'accéder à un serveur placé derrière NAT de à la fois Internet et LAN. L'utilisation de deux zones DNS est une alternative viable, mais pas toujours la solution. Mais la solution existe et est incroyablement simple (mais pas parfaite, probablement):

(1) sur le serveur: ajoutez l'adresse IP publique en tant qu'adresse IP secondaire sur l'interface réseau du serveur avec le masque 255.255.255.255 (le service Web ou tout ce que vous voulez sur le serveur doit également écouter sur cette adresse IP); tous les systèmes d'exploitation modernes vous permettront de le faire (ou une interface de bouclage avec l'adresse IP publique qui lui est attribuée peut être utilisée au lieu d'ajouter une adresse IP secondaire à l'interface principale).

(2) sur les hôtes LAN: ajoutez une route Host pour l'adresse IP publique, par exemple, pour les hôtes Windows, utilisez la commande suivante: route -p add 203.0.113.130 mask 255.255.255.255 192.168 1.11 (vous pouvez également utiliser l'option DHCP "route statique" pour distribuer la route). Ou, s'il y a un (des) commutateur (s)/routeur (s) L3 entre les clients et le routeur Internet, configurez cet itinéraire hôte sur ce (ces) commutateur (s)/routeur (s) intermédiaire (s), pas sur les clients.

Pour ceux qui concernent la TCP poignée de main à trois voies: cela fonctionnera bien dans la configuration proposée.

Veuillez fournir des commentaires (au moins, voter).

2
Sergio

D'un point de vue technique, la meilleure solution à ce problème est d'activer IPv6 sur votre réseau. Lorsque IPv6 est activé, vous devez créer un enregistrement AAAA pour votre domaine. Gardez l'enregistrement A existant pointant vers l'IPv4 externe du routeur . Créez un enregistrement AAAA pointant vers l'adresse IPv6 du serveur .

IPv6 a suffisamment d'adresses pour éviter le NAT, vous n'aurez donc pas besoin d'épingle à cheveux NAT pour IPv6. Et une fois que vous avez activé IPv6 et créé des enregistrements AAAA, tout client prenant en charge RFC 8305 essaiera IPv6 avant IPv4. Cela signifie que vous n'avez pas besoin non plus d'épingle à cheveux NAT pour IPv4, car les clients ne l'utiliseront pas.

Vous aurez toujours besoin de votre IPv4 existant NAT pour les connexions sortantes et la redirection de port pour les connexions entrantes jusqu'à ce que la plupart du monde ait également activé IPv6.

C'est aussi plus rapide.

L'utilisation d'IPv6 vous donnera de meilleures performances que le NAT en épingle à cheveux.

Avec l'épingle à cheveux NAT votre client enverra un paquet via un commutateur au routeur, le routeur effectuera ensuite deux tours de traduction et enverra finalement le paquet via le commutateur au serveur. Paquets du serveur au client passera par tout ce chemin à l'envers.

Avec IPv6, vous évitez le NAT, à la place, les paquets sont envoyés directement via le commutateur entre le client et le serveur. Cela signifie que sur un aller-retour, vous réduisez le nombre de passages à travers le commutateur de 4 à 2, et vous évitez 2 voyages à travers le routeur et les 4 traductions que le routeur aurait effectuées. Cela se traduit par de meilleures performances.

Cela est vrai même si vous utilisez un commutateur intégré au même boîtier que le routeur.

Que faire si le FAI n'a pas IPv6?

Si vous utilisez un FAI qui ne prend pas en charge IPv6, je me demanderai si vous devez héberger des serveurs sur ce réseau. Ce sont mes suggestions sur ce qu'il faut faire si le FAI ne prend pas actuellement en charge IPv6.

Dites d'abord au FAI que vous avez besoin IPv6. Et rappelez-leur peut-être que le protocole IPv6 existe depuis 20 ans, donc ils sont attendus depuis longtemps pour le soutenir. Si cela ne suffit pas pour que le FAI vous prenne au sérieux, commencez à chercher d'autres FAI.

Si vous trouvez un FAI avec prise en charge IPv6, vous pouvez exécuter les deux FAI pendant une période de transition. Sur le routeur connecté au nouveau FAI, vous pouvez désactiver IPv4 côté LAN, puis connecter les côtés LAN des deux routeurs au même commutateur. IPv4 et IPv6 sont deux protocoles indépendants et, en tant que tels, cela ne pose aucun problème si ces connexions passent par des routeurs différents. Comme avantage secondaire, il vous donne une certaine redondance si l'une des connexions a une panne.

Si vous ne trouvez pas de FAI avec prise en charge IPv6, vous devriez envisager de déplacer votre serveur vers un centre d'hébergement. Avec un serveur dans un centre d'hébergement, vous êtes moins dépendant de la situation géographique et pour cette raison, il y a plus de concurrence entre les fournisseurs, ce qui vous aidera à en trouver un qui répond à vos besoins.

Déplacer le serveur vers un centre d'hébergement ne donnera pas IPv6 à vos clients, mais déplacer le serveur signifie que vous n'avez plus besoin d'épingle à cheveux NAT pour l'atteindre).

Ce que vous ne devez pas faire

N'activez pas IPv6 et ne créez pas d'enregistrements AAAA si vous n'avez aucun moyen d'acheminer le trafic IPv6. Si votre FAI ne prend pas en charge IPv6 mais que vous choisissez d'activer de toute façon IPv6 sur votre réseau local (peut-être en utilisant des adresses RFC 4193) et de créer des enregistrements AAAA, cela fonctionnera pour les clients de votre réseau local atteignant le serveur sur votre réseau local. Mais la communication entre votre réseau local et le monde extérieur essaierait d'abord IPv6 (qui ne fonctionnerait pas), et vous vous reposeriez sur le retour à IPv4 qui, au mieux, est un peu plus lent ou, au pire, ne se produit pas.

1
kasperd

Mauvaise réponse à mes questions juste pour élargir les horizons de ceux qui ont des problèmes similaires.

J'ai été contacté par mon FAI et je leur ai demandé d'essayer de résoudre mes problèmes. Ce qu'ils m'ont offert est une autre adresse IP publique juste pour le serveur, maintenant j'ai du trafic local du côté WAN de FreeBSD et nous avons créé des canaux spécifiques pour un débit plus rapide du trafic local vers l'IP publique du serveur)

1
adopilot

J'ajouterai une réponse ici car les commentaires ici n'ont pas abordé mon problème particulier. Je soupçonne que c'est parce que j'ai rencontré un bug de noyau Linux désagréable. La configuration est la suivante:

internet <--> modem 1.1.1.1/30 <--> switch <---> LAN 10.1.1.0/24
                                      ^
        +----------------------+      |
        |              /--eth0 o <----/
        |              |       |           
        | 10.1.1.1/24 br0      |           v (antenna)
        |  1.1.1.2/30  |       |           |
        |              \-wlan0 o ----------/
        +----------------------+ 

Malgré l'image complexe, le seul changement pertinent aux situations couvertes dans d'autres commentaires est l'ajout du pont logiciel, br0. C'est là parce que le boîtier de passerelle est également un point d'accès sans fil pour le LAN.

Notre boîtier de passerelle exécute toujours NAT tâches pour les machines sur le LAN. Parce qu'il n'a qu'un seul port Ethernet, il est obligé de faire du NAT en épingle à cheveux. Je soupçonne qu'il devrait simplement fonctionner avec les règles iptables données dans d'autres commentaires ici, mais sur le noyau Linux 4.9 du moins, ce n'est pas le cas. Sous 4.9, notre boîte de passerelle peut accéder à Internet, les machines du LAN essayant d'y accéder via NAT can 't.

tcpdump montre les réponses aux paquets entrants frappant eth0, mais ils ne sortent pas de br0. L'exécution de cette commande corrige les problèmes suivants:

ebtables -t brouter -A BROUTING -d 01:00:00:00:00:00/01:00:00:00:00:00 -j ACCEPT
ebtables -t brouter -A BROUTING -p IPv4 --ip-dst 10.1.1.0/24 -j ACCEPT
ebtables -t brouter -A BROUTING -p IPv4 --ip-src 10.1.1.0/24 -j ACCEPT
ebtables -t brouter -A BROUTING -p IPv4 -j DROP

Avant que cette commande ne soit exécutée, les paquets entrants sont traités selon le comportement par défaut des noyaux, qui est de les donner au pont puis de leur passer les modules de routage du noyau. La commande force les paquets qui ne sont pas du LAN à contourner le pont et à passer directement au routage, ce qui signifie que le pont n'a pas la possibilité de les supprimer. Les adresses de diffusion et de multidiffusion doivent être pontées, sinon des choses comme DHCP et mDNS ne fonctionneront pas. si vous utilisez IPv6, vous devez également lui ajouter des règles.

Vous pourriez être tenté de résoudre le problème en utilisant ceci:

brctl hairpin br0 eth0 on
brctl hairpin br0 wlan0 on

J'étais certainement tellement tenté - c'était ma première tentative. Dès que je l'ai fait, les machines sur le LAN ont accédé à Internet, donc cela fonctionne pendant un certain temps. Ensuite, les événements suivants se sont produits (et je n'ai pas voulu répéter l'expérience):

  1. Les temps de ping à travers le LAN vers la passerelle ont doublé à environ 10 secondes d'intervalle, passant de 0,1 ms à 0,2 ms, 0,4 ms, 0,8 ms, 2 ms et ainsi de suite jusqu'à ce que la boîte de la passerelle soit inaccessible depuis le LAN. Cela sentait comme une tempête de paquets, mais STP était allumé partout.
  2. Peu de temps après la mort de tous les points d'accès sans fil.
  3. Tout en essayant de diagnostiquer ce qui se passait avec le sans fil, tous les téléphones IP ont redémarré.
  4. Peu de temps après, les machines câblées ont perdu tout contact avec le LAN.

La seule issue était de redémarrer toutes les machines du bâtiment. La seule exception était les commutateurs matériels, qui ne pouvaient pas être redémarrés. Ils devaient être mis hors tension.

0
Russell Stuart

Depuis que j'ai également posé cette question (voir Comment puis-je accéder à un service réseau NATed derrière un pare-feu de l'intérieur en utilisant son IP externe? ) et a été redirigé ici mais les réponses ici ne fournissent pas de solution (contrairement aux explications génériques ) laissez mon fournir mon Linux (iptables specific) ici pour économiser à tout le monde quelques heures d'expérimentation. Ce fichier est dans iptables-restore format et peut être lu directement dans iptables (après avoir bien sûr modifié les adresses IP). Il s'agit d'un serveur Web (port 80) et uniquement pour IPv4 - les règles pour IPv6 et pour SSL (port 443) sont analogues.


# Port forwarding for VM / Container access with „hairpin NAT“.
*nat
:PREROUTING ACCEPT [3:205]
:INPUT ACCEPT [59:670]
:OUTPUT ACCEPT [16:172]
:POSTROUTING ACCEPT [20:257]

# This was simple port forwarding - access works from outside but not from inside
#-A PREROUTING  -4 -p tcp -i eth0 --dport 80 -j DNAT --to web.local:80

# This is real hairpin NAT which allows „web.local“ to access itself via the VM hosts external IP.
# First we need to masquerade any traffic going out the external interface:
-A POSTROUTING -o eth0 -j MASQUERADE

# Then we need to reroute incoming traffic on the public IP to the local IP:
-A PREROUTING  -4 -p tcp -d web.public.com --dport  80 -j DNAT --to web.local:80

# And finally we need to tell the router that the source IP of any traffic
# coming from the LAN must be source-rewritten when going to the web server:
-A POSTROUTING -4 -p tcp -s lan.local/24 -d web.local --dport  80 -j SNAT --to-source web.public.com:80

COMMIT

Remplacer lan.local, web.local et web.public.com avec votre réseau local (par exemple 10.0.x.0/24), l'IP locale de votre serveur Web (par exemple 10.0.1.2) et l'IP publique de votre routeur (par exemple 4.5.6.7). Le -4 consiste simplement à autoriser les règles IPv6 et IPv4 dans le même fichier (ces lignes ignorées par ip6tables). N'oubliez pas non plus de mettre les adresses IPv6 entre [crochets] lorsqu'elles incluent des déclarations de port, par ex. [fe0a:bd52::2]:80.

Ce sont toutes ces choses qui m'ont fait arracher mes cheveux en essayant d'implémenter les explications de cette question. J'espère que je n'ai rien oublié.

0
Jens

Comme c'est une question canonique. Je répondrai si vous avez un routeur Sonicwall.

L'expression à connaître est politique de bouclage NAT

Ce document décrit comment un hôte sur un réseau local SonicWall peut accéder à un serveur sur le réseau local SonicWall en utilisant l'adresse IP publique du serveur au nom de domaine complet. Imaginez un réseau NSA 4500 (SonicOS Enhanced) dans lequel le sous-réseau LAN principal est 10.100.0.0/24 et l'IP primaire WAN est 3.3.2.1. disons que vous avez un site Web pour vos clients, et que son nom d'hôte est. Vous avez déjà écrit les politiques et les règles nécessaires pour que les étrangers puissent accéder au site Web, mais il fonctionne vraiment sur un serveur côté privé 10.100.0.2. Imaginez maintenant que vous êtes une personne utilisant un ordinateur portable sur le côté privé, avec une IP de 10.100.0.200. Vous voulez atteindre le serveur en utilisant son nom public, car vous faites la même chose lorsque votre ordinateur portable est avec vous sur la route. Si vous vous asseyez sur le côté privé, et demande http://www.example.com >, le bouclage est ce qui permet que cela fonctionne, même si le serveur est en fait juste à côté de vous sur une adresse IP locale .

Pour autoriser cette fonctionnalité, vous devez créer une politique de bouclage NAT, également appelée NAT réflexion ou épingle à cheveux).

Stratégie de bouclage utilisant WAN Adresse IP de l'interface

Login to the SonicWall Management GUI.
Navigate to Manage | Rules | NAT Policies submenu.
Click on the Add button.
Create the following NAT Policy.
Original Source: LAN Subnets (or Firewalled Subnets if you want hosts in other zones to be included)
Translated Source: WAN Interface IP
Original Destination: WAN Interface IP
Translated Destination: (LAN server object)
Original Service: Any
Translated Service: Original
Inbound Interface: Any
Outbound Interface: Any

Le sonicwall reconnaîtra le service externe que vous essayez de contacter et réécrira l'adresse de destination pour l'adapter à l'adresse interne du serveur, elle sera donc transparente pour l'ordinateur.

0
yagmoth555