1

Problem.

Hi all,

I am in the need of having a small number of virtual machines living in a particular server. Each machine should have its own proxy configuration, but the software running in them does not have proper proxy setting capabilities so proxy configuration at the guest is not an option. My goal is to route as much traffic as my external proxy allows, not just HTTP.

I am using VirtualBox running on a Ubuntu server, connected to a router that has Tomato firmware (think of it as a tiny Linux box). The VMs are connected to the router through a bridged connection, so the router sees each of them independently; I would strongly prefer to keep it that way because it is extremely convenient to be able to talk to each of the VMs by its IP (I can set that up to be static). I am open to using other server-side software but I don't see a reason why my current setup wouldn't work. I have thought of a few different options, and I would like to know if anyone has some insight on which would be best or if I am missing a better option altogether:

Option 1.

I have been able to successfully install and configure a squid3 proxy server on my Ubuntu server (the same one that runs the VMs), which communicates with the authenticated proxies in the wild. For security reasons, I enabled only local connections to the proxy and other machines in the same network are able to use the connect to the local proxy which in turns redirects them to the external proxy:

Local Machine -> Ubuntu Server (squid3) -> External Proxy

Unfortunately, as I mentioned above, the VMs do not have proxy client capabilities. I thought that I could route all of the server's traffic through its own Squid server, but since the VMs have a bridged connection they talk to the router directly. To mitigate that problem, I have been trying to redirect the VMs traffic from the router back to the Ubuntu Server:

Virtual Machine -> Tomato Router -> Ubuntu Server (squid3) -> External Proxy

I have had little success with this approach so far, since I am getting lost in the details of how to redirect the traffic for all ports and I have never done any work with iptables before. Even if I was able to redirect all traffic back to the squid3 server, I don't know how I would be able to apply individual proxy settings to each of the VMs. Would I need to set up a squid3 server for each of the VMs? I am pretty sure that squid3 allows me to filter by incoming IP but the cache_peer "proxy-host" parent "proxy-port" 0 no-query default login=username:password option that I am using to talk to the external proxies seems to behave globally.

Option 2.

I could install a squid3 proxy server on the Tomato router and do all of what I described in the first option on the router itself, but I have not been able to install the proxy server yet. Just like I was wondering in the first option, would I need a different proxy server for each of the VMs? The layout would be very similar:

Virtual Machine -> Tomato Router (squid3) -> External Proxy

Option 3.

Even though I would prefer to maintain the bridged connection from the VMs to the router, perhaps there is a way to connect to the VMs through NAT and using the squid3 server either on the Ubuntu Server or the Tomato router (if I am able to make it work).

Question.

Which option would be the best way around my problem? Is there a better way to approach this that I have not considered?

Update.

Apparently I was mistaken about squid being unable to handle the cache_peer directive on a client basis rather than globally, I can simply use cache_peer_access. Currently, I am trying to go for option 1 until someone gives me a better reason not to. This is the configuration that I have for /etc/squid3/squid.conf:

Edit: Updated http_port as per suggested

# acl definitions here
acl localnet src 192.168.1.0/24
acl localhost src 127.0.0.1

# Only allow cachemgr access from localhost
http_access allow localhost manager
http_access deny manager

# any client in the local network has access
http_access allow localhost
http_access allow localnet

# And finally deny all other access to this proxy
#http_access deny all
http_access allow all # test only

# external proxy settings
http_port 3128 transparent
cache_peer XXXX.XXXX.XXXX.XXXX parent 80 0 no-query default login=user:pass

# No direct access
never_direct allow all

# do not forward the IP address
forwarded_for off

Traffic is being redirected from the Tomato router to my squid server. To do that, I am using the following iptables (the VMs are limited to the ips in the range 192.168.1.50-192.168.1.100 enforced by statically binding the MAC address to an IP through the DHCP server):

PROXY_IP=192.168.1.115
REDIRECT_PORTS=443,80,21,70,210,1025:65535,280,488,591,777
iptables -t mangle -A PREROUTING -p tcp --dport 80 -s $PROXY_IP -j ACCEPT
iptables -t mangle -A PREROUTING -m iprange --src-range 192.168.1.50-192.168.1.100 -p tcp -m multiport --dport $REDIRECT_PORTS -j MARK --set-mark 3
iptables -t mangle -A PREROUTING -m iprange --src-range 192.168.1.50-192.168.1.100 -p udp -m multiport --dport $REDIRECT_PORTS -j MARK --set-mark 3
ip rule add fwmark 3 table 2 
ip route add default via $PROXY_IP dev br0 table 2

And then back in the Ubuntu server:

iptables -A PREROUTING -t nat -p tcp -m multiport --dport $REDIRECT_PORTS -j REDIRECT --to 3128
iptables -A PREROUTING -t nat -p udp -m multiport --dport $REDIRECT_PORTS -j REDIRECT --to 3128
  • "http_port 127.0.0.1:3128" - makes it accessible only from the server itself. Change to "http_port 3128". – Veniamin Nov 15 '13 at 12:31
  • Reverse routing is a bad idea, it may fall into routing loop. – Veniamin Nov 15 '13 at 12:32
0

I suppose your very first option will be Ok.

But you should configure VMs to use the host server as a default gateway, disable icmp redirects on the server, and setup transparent http proxy on it.

UPD:

Changing icmp redirects and VM's routing is not needed if your bridge calls for iptables.

/etc/sysctl.conf:

net.ipv4.ip_forward = 1    
net.bridge.bridge-nf-call-iptables = 1

To redirect http requests to your squid, iptables:

iptables -t nat -A PREROUTING -p tcp -m tcp --dport 80 -j REDIRECT --to-ports 3128
  • I can't configure the VMs to use a gateway other than the router... – Oscar Wahltinez Nov 15 '13 at 8:15
  • I see that you updated your answer. Where would that configuration go, exactly? The router? The squid server and the router are on two different boxes – Oscar Wahltinez Nov 15 '13 at 8:16
  • @omtinez exactly on the server hosting VMs and running squid. No modifications on the tomato box are needed. – Veniamin Nov 15 '13 at 11:41
  • Why would the VMs listen to that configuration? To my understanding, they are talking "directly" to the router (I selected bridged connection as an option for the VMs in Virtualbox). I thought that the networking happened transparently to the server – Oscar Wahltinez Nov 15 '13 at 18:29
  • Just a magic "net.bridge.bridge-nf-call-iptables = 1" - makes a bridged traffic to go to iptables. = – Veniamin Nov 15 '13 at 19:24

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.