1

We need a way to insert a device between a target device and the network, ideally without needing to change any IP addresses.

Currently, the situation is (please excuse the ASCII art)

-----------       -------------
| x.x.x.5 | ----- | x.x.x.10  |
-----------       -------------

What we are trying to do is insert a device with two network interfaces, and what we'd LIKE to do is arrange the IPs so each side thinks it's talking to the orignal device. We'll take care of moving the data from one interface to the other.

-----------     --------------------------------    ------------
| x.x.x.5 | --- | eth0 x.x.x.10   x.x.x.5 eth1 |--- | x.x.x.10 |
-----------     --------------------------------    ------------

Is there a way to setup the routing table such that a request for x.x.x.10 that comes in from eth0 gets sent out eth1, and requests for x.x.x.5 that arrive via eth1 get sent out eth0?

The middle box is running Linux.

1
  • 3
    Why did you state 'Unfortunately, it won't work" to the suggestion using a bridge? Your schema looks most similar to a bridge. You should provide more information about the network. Are x.x.x.5|10 within the same net/subnet? Is it a gateway between LAN / WAN? You are providing very poor information for now, so that answers can only guess around. May 28, 2017 at 1:58

3 Answers 3

4
+50

You can do this with a VPN that can work at Layer 2, like OpenVPN ethernet bridging. See https://openvpn.net/index.php/open-source/documentation/miscellaneous/76-ethernet-bridging.html

Another way to do it is with MPLS tunnel. See: http://blog.ine.com/2010/08/26/mpls-tunnels-explained/

If you want just packet inspection, like an IDS, you can use for example snort. See: http://sublimerobots.com/2016/02/snort-ips-inline-mode-on-ubuntu/

1
  • 1
    +1 for OpenVPN Ethernet bridging. May 27, 2017 at 23:59
3

Maybe you can configure a bridge using bridge-utils. That way you don't even need to configure those IP addresses on the middle box.

This of course depends on why you need to have this box in between.

2
  • I hadn't heard of bridge-utils before, so thank you. Unfortunately, it won't work. I'm doing some tunneling (so in reality there will probably be two devices between the original devices, but that's a separate issue that can be resolved if I can figure out this one).
    – DougN
    May 13, 2017 at 20:18
  • 1
    If there are multiple devices, you could use gre or vtun to create the (layer 3) tunnel between these devices, and connect everything up using bridge-utils on both sides so it appears to be a direct layer 2 connection.
    – Cheatah
    May 13, 2017 at 20:23
2

It is not clear why you want to give these specific addresses to your middle box. If you just need to pass packets to the other end, there is no need for that, you can use bridging (or optionally proxy-arp).

One valid use case if you want traffic from either end to be directed to an application running locally on the middle box, optionally generating a new application request on the other side, going up and down the full network stack (for instance, say, a userland HTTP proxy). If this is what you want, keep reading.

You cannot configure the middle box like this as-is, because the middle box will not be able to distinguish its local interface on one side, from the remote interface on the other side.

The way I would try to set it up, would be first to chose two new addresses for the middle box, splitting one side into a separate subnet. for instance x.x.x.6/30 (that blocks .4 and .7 as network addresses, from the middle box, and allows .5 for the remote side) and x.x.x.11 for the other side.

Next, enable proxy-ARP for the two relevant interfaces, by adding the following to your interface startup scripts:

 echo 1 >/proc/sys/net/ipv4/conf/eth0/proxy_arp

for eth0, and

 echo 1 >/proc/sys/net/ipv4/conf/eth0/proxy_arp

for eth1. You can also use all instead of the interface name, if there are no other interfaces on the box. This will have the effect that your middle box will now respond with its own MAC address to arp requests directed at known routable addresses on the other side.

Next, use these four NAT rules to make the box invisible:

iptables -t nat -A PREROUTING -i eth0 -s x.x.x.5 -d x.x.x.10 -j DNAT --to-destination x.x.x.6
iptables -t nat -A POSTROUTING -o eth0 -d x.x.x.5 -s x.x.x.6 -j SNAT --to-source x.x.x.10
iptables -t nat -A PREROUTING -i eth1 -s x.x.x.10 -d x.x.x.5 -j DNAT --to-destination x.x.x.11
iptables -t nat -A POSTROUTING -o eth1 -d x.x.x.10 -s x.x.x.11 -j SNAT --to-source x.x.x.5

This way, you get to use different addresses internally to identify the interfaces of your middle box, but they don't appear in the outside. The process will look like:

  • x.x.x.5 makes a direct ARP request for x.x.x.10. This requests arrives on the middle box on eth0.
  • middle box notices that x.x.x.10 is routable on eth1, so answers with its own MAC address
  • the IP packet to x.x.x.10 gets delivered to middle box on eth0
  • DNAT rule in PREROUTING eth0 kicks in and rewrites the destination to x.x.x.6
  • local application handles the request to x.x.x.6, issues a separate request to x.x.x.10, the request gets routed to eth1
  • SNAT rule in POSTROUTING eth1 kicks in, changes the source address to x.x.x.5
  • x.x.x.10 sees the middle box request arriving from x.x.x.5.
  • x.x.x.10 wants to reply, issues ARP request for x.x.x.5
  • proxy-arp kicks in on eth1, since x.x.x.5 is routable on eth0
  • reply goes to middle box, DNAT rule in eth1 kicks in, rewrites the destination to x.x.x.11
  • local application handles the response, the original process issues a response from x.x.x.6 to x.x.x.5
  • SNAT rule for eth0 kicks in, changes the source address to x.x.x.10
  • final response is issued to x.x.x.5

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .