FreeS/WAN Opportunism HowTo =========================== RCSID $Id: opportunism.howto,v 1.9.6.1 2002/02/05 01:30:10 henry Exp $ D. Hugh Redelmeier FreeS/WAN, the LINUX IPSEC implementation, is intended to allow systems to connect through secure tunnels with or without prearrangement. We use the term "Opportunism" to describe tunnels set up without prearrangement. This HowTo will show you how to set your system up for Opportunism. You are expected to already have built and used FreeS/WAN. Much more information about FreeS/WAN is provided at http://www.freeswan.org. This document is only intended to describe the support for opportunism. The features described here are available in FreeS/WAN version 1.91 or later (there were important bugs up until 1.95). For a more complete description of the design of Opportunism, see our paper "Opportunistic Encryption" (available as opportunism.spec in the same directory as this document). Steps ===== - Understand what you are attempting. Security requires care. Problems are hard to untangle. Be sure to read the last section "Important Limitations". - Install FreeS/WAN (version 1.91 or later). - Add appropriate DNS records to your reverse-map domains. - Add suitable conns to /etc/ipsec.conf. - Try it out: start it, monitor it, fix it. - Now you understand the system better, reread "Important Limitations" These steps are also an outline of this document. Theory ====== FreeS/WAN runs on a machine that we will call a "Security Gateway". Usually this machine is a gateway to the internet. It may be that the only machine for which it provides gateway services is itself, but that is just a special case -- we will still call it a Security Gateway. A FreeS/WAN Security Gateway implements secure tunnels to other Security Gateways. One problem is to arrange for these tunnels to be created and used. If opportunism is enabled, a Security Gateway running FreeS/WAN will intercept the first outbound packet to a particular destination (IP address), and try to negotiate a security tunnel suitable for traffic to that destination. To make this work going the other way, the Security Gateway must be willing to negotiate with peers trying to protect traffic initiated from their side. The first novel problem is that our Security Gateway needs to discover the IP address of the other Security Gateway for the packet that prompted the negotiation. Oh, and quickly discover if there is none -- that negotiation will be impossible. The second novel problem is that our Security Gateway needs to authenticate the other Security Gateway. This authentication needs to ensure that the other Security Gateway is who it claims to be AND that it is authorized to represent the client for which it claims to be the gateway. The roles in a particular negotiation are: Source----Initiator----...----Responder----Destination The Source and Destination are endpoints of the traffic that is to be protected. The Source is the one that happened to send the first packet of traffic. Neither needs to be aware of IPSEC or FreeS/WAN. That is the job of their respective Security Gateways, Initiator and Responder. The names "Initiator" and "Responder" match those used in the IPSEC standards for IKE negotiation. Remember that Source and Initiator could be the same machine; similarly, Destination and Responder could be the same. All traffic from Source or Destination must flow through their Security Gateways if it is to be considered for protection. These roles are fluid -- they can be different for each negotiation. We use the DNS (the Domain Name System) as a distributed database to publish the required information. DNS Records Required ==================== See section 2.3 of "Opportunistic Encryption" for a fuller explanation. Generally, we need to add records to the reverse-map DNS entries for the client machine and its Security Gateway machine. There are special cases that are exceptions. A Security Gateway that is going to initiate an Opportunistic negotiation needs to provide a way for the Responding SG to find a public key for the Initiator to allow authentication. This is accomplished by putting the public key in a KEY record in the reverse-map of the Initiator. Conveniently, the KEY record can be generated by the ipsec_showhostkey(8) command. ipsec showhostkey Here is an example of the output, with many characters of the key itself left out: ; RSA 2048 bits xy.example.com Sat Apr 15 13:53:22 2000 xy.example.com. IN KEY 0x4200 4 1 AQOF8tZ2...+buFuFn/ => Copy the output of the command into the zone information for the reverse-map of the Security Gateway's public interface. Each client that is to be protected by Opportunistic Encryption must include a special TXT record in its reverse-map. The ipsec_showhostkey(8) command can create this too. Remember: this command must be run on the Security Gateway where the ipsec.secrets file resides. You must tell the command what IP address to put in the TXT record. The IP address is that of the Security Gateway. ipsec showhostkey --txt 10.11.12.13 This command might produce the output: ; RSA 2048 bits xy.example.com Sat Apr 15 13:53:22 2000 IN TXT "X-IPsec-Server(10)=10.11.12.13 AQOF8tZ2...+buFuFn/" - The quotes matter: this is a single string, as far as DNS is concerned. - The X-IPsec-Server is a prefix that signifies that the TXT record contains Opportunism configuration information. - The (10) specifies a precedence for this record. This is similar to MX record preferences. Lower numbers have stronger preference. - 10.11.12.13 specifies the IP address of the Security Gateway for this machine. - AQOF8tZ2...+buFuFn/ is the (shortened) encoding of the RSA Public key of the Security Gateway. => Added this output to the zone information for the reverse-map for each client machine. This gets a bit dull and repetitive. Unfortunately, not every administrator has control over the contents of the reverse-map. The only case where we can work around this is where the Initiator has no suitable reverse map. In this case, the Source's TXT record gives @FQDN ("Fully Qualified Domain Name") in place of its Security Gateway's IP address. This FQDN must match the ID-payload used by the Initiator. Furthermore, a forward lookup for a KEY record on the FQDN must yield the Initiator's public key. If the Source's IP address is the same as the Initiator's IP address, the Responder will assume that the Initiator is authorized to talk for the Source (itself!). In this case, the Responder won't try to fetch the Source's TXT record from the reverse map for the Source's IP address. These two features can be combined. If the Source and the Initiator are the same (i.e. the Security Gateway is protecting itself), and the Initiator uses a @FQDN ID (leftid=@example.com), then the administrator of that machine need only have installed a KEY record in the FQDN domain -- he need not control any reverse map. Obscure fact: the forward lookup is only done by a Responder, and then only when the Initiator's ID payload specifies the FQDN. There is no provision for a Responder with no control over its reverse-map. Beware: DNS changes sometimes take a long time to propagate. Configuring FreeS/WAN ===================== To enable opportunism, you must include a suitable conn in /etc/ipsec.conf and you must enable it. A suitable conn looks roughly like an ordinary conn. It more closely resembles a Road Warrior conn (a Road Warrior conn is one that has a wildcard %any specified as the other Security Gateway). But in the Opportunistic case, both the other Security Gateway AND its client are unknown ahead of time. conn client-to-anyone # for our client subnet leftsubnet=10.3.2.1.0/24 # any single client in our subnet also=sg-to-anyone # rest is same as for SG conn sg-to-anyone # for our Security Gateway left=%defaultroute # our SG (defaults leftnexthop too) right=%opportunistic authby=rsasig # almost always the right choice keyingtries=2 # don't be persistent -- peer might disappear auto=route # enable at ipsec startup (%defaultroute only works if you have specified interfaces=%defaultroute. Since this isn't the topic of the howto, you will have to look at the other documentation to find out how to handle other cases.) You can have any number of opportunistic conns, but generally it only makes sense to have one for each client subnet and one for the Security Gateway itself. Currently only one interface may be used for opportunism: Pluto knows nothing about routing, so would be unable to choose amongst several. Almost certainly our side's nexthop must be predetermined (%defaultroute will do that). Note: the routing done for outbound Opportunism will catch any packets not covered by a more specific route. This is what you want for packets that are also covered by an eroute. But packets caught by the route and not an eroute will be subject to the no-eroute policy of KLIPS, which defaults to %drop. Remember that routing ignores the packet's source address, but erouting pays attention to it. So if Opportunism is enabled, it is best to provide for it covering all IP addresses behind or on the Security Gateway. To enable these conns for inbound opportunistic negotiation, they must be --added. auto=add would accomplish this at ipsec startup, but if you cannot wait: ipsec auto --add sg-to-anyone ipsec auto --add client-to-anyone To enable these conns for outbound opportunistic negotiation, they must be both --added and --routed. Outbound packets will then be trapped and will trigger negotiation. auto=route would cause this to happen at startup, but if you wish to do this at another time: ipsec auto --add sg-to-anyone ipsec auto --add client-to-anyone ipsec auto --route sg-to-anyone ipsec auto --route client-to-anyone Getting DNS Through =================== There is a serious chicken-and-egg problem. Outbound Opportunism blocks communication with an IP address until Pluto discovers whether that IP address can have an IPSEC connection negotiated. This discovery takes DNS queries. These DNS queries might involve communicating with arbitrary IP addresses. Thus we require DNS queries to succeed before any communication succeeds, including those same DNS queries! The way out of this conundrum is to exempt at least some DNS query IP traffic from Opportunism. There are several possible solutions, all of which have advantages and disadvantages. 1. If you use a single machine, outside your Security Gateway, as DNS server, you can build a clear path (or even an IPSEC tunnel, but not opportunistically) directly to that machine. - you could use a type=passthrough conn to provide a clear path between your machine and the DNS machine. - better still, you could explicitly create an IPSEC connection to your DNS server. Just be sure that Pluto does not need to access DNS to find the IP addresses or RSA public keys for that connection! - you could install an explicit route to the DNS machine through your public interface (not ipsecN). This will bypass KLIPS processing. You might have to adjust your firewall. For example: route add host -net ns.example.com gw gw.example.com dev eth1 2. Generally, it is better to run DNS on your Security Gateway. This leads to a need for non-opportunistic paths to an arbitrary number of DNS servers in the internet. One way to accomplish this is to NOT have outbound opportunism cover the SG itself, but only the subnet behind it. In other words, leave out the ipsec auto --route sg-to-anyone You must also add a type=passthrough eroute specifically for sg-to-anyone (without this, the traffic will be handled by the KLIPS no-eroute policy). 3. It is actually possible to use a single machine inside your client subnet as a DNS server. The techniques listed in 1 could be used to let it communicate with other DNS servers without interference. This might have advantages over 1 if the DNS machine *only* did DNS. Another technique (not often possible or reasonable) is to give this machine another route to the internet, one that avoids the SG. 4. DNS queries will eventually time out and then Pluto will give up and establish %pass eroutes. So communications should start flowing. We would like to have better solutions. Perhaps we will in the future. Suggestions are welcome. Figuring out what is going on ============================= Since Opportunism lets your SG operate with less supervision, you may be puzzled by what it is up to. The usual tools exist, but their use is more important. To look at what Pluto is doing, use: ipsec auto --status To look at what KLIPS is doing, use ipsec look To just see the kernel's eroute table, look at the "file" /proc/net/ipsec_eroute. It contains a description of all the eroutes in the kernel. Here is an example: 10 10.2.1.0/24 -> 0.0.0.0/0 => %trap 259 10.2.1.115/32 -> 10.19.75.161/32 => tun0x1002@10.19.75.145 71 10.44.73.97/32 -> 0.0.0.0/0 => %trap 4119 10.44.73.97/32 -> 10.114.121.41/32 => %pass You read each line as: a packet from within the first subnet, destined for the second subnet, will be processed by the Security Association Identity (SAID) specified last. The first column is the number of (outbound) packets processed by this eroute. For shunt eroutes, the SAID is printed as just the type of shunt: %pass pass the packet through with no processing %drop discard the packet %reject discard the packet and notify sender %hold keep the last packet; discard others %trap cause any trapped packet to generate a PF_KEY ACQUIRE to request negotiation; install a corresponding %hold shunt and attach this packet to the %hold For other eroutes, the SAID is printed as a triple: protocol (three letters), SPI (32-bit number in hex), and destination IP address. Protocols include: tun IP in IP encapsulation (used for most tunnels) esp ESP encapsulation -- part of an IPSEC SA group ah AH packet authentication -- part of an IPSEC SA group So, looking at our sample eroutes: 10 10.2.1.0/24 -> 0.0.0.0/0 => %trap This is a TRAP (int0x104) shunt eroute. It was installed by Pluto so that it can catch all traffic from its client subnet to the world at large. Ten outbound packets have been trapped. 259 10.2.1.115/32 -> 10.19.75.161/32 => tun0x1002@10.19.75.145 This is a tunnel eroute: packets from 10.2.1.115 (within our client subnet) going to 10.19.75.161 will be encrypted and sent to the peer SG 10.19.75.145. This was the product of an Opportunistic negotiation (a hint is that each client subnet has only one member). 259 packets have been sent through this tunnel. 71 10.44.73.97/32 -> 0.0.0.0/0 => %trap This is another TRAP shunt eroute. It is to catch traffic from the Security Gateway to the world. It has caught 71 outbound packets. 4119 10.44.73.97/32 -> 10.114.121.41/32 => %pass This is a %pass (0x100) shunt eroute. It was installed when an attempted Opportunistic negotiation failed because the reverse domain of 10.114.121.41 had no suitable TXT record. 4119 outbound packets have been passed. Important Limitations ===================== Pluto's DNS lookup is synchronous (single-threaded). Not only does this slow things down, but it turns out that in extreme cases where there are a lot of ACQUIRE messages from KLIPS at once, some of those messages can be lost and communications will be blocked by the %hold eroute that Pluto doesn't know about. Pluto now looks every 2 minutes for any %holds that it missed. DNS lookup is not verified -- we don't use Secure DNS. A spoofed DNS could compromise Opportunism. There are several new opportunities for Denial of Service attacks. For example, a Bad Guy could spray our system with pings with forged source addresses. For each unique source address, our system would do a (synchronous!) DNS lookup. Once a %pass eroute is added for a failed negotiation, it will stay until it has been inactive for about 15 minutes. The only activity that counts is outbound -- not surprising since a %pass only affects outbound traffic. If a destination's DNS entry specifies the information we need for negotiation, Pluto will not let communications proceed without negotiating a Security Tunnel. There is currently no way to tear down a tunnel that is no longer in use. To add insult to injury, when the lifetime is about to be exceeded, the initiating Pluto will rekey! Restarting will clear these out. rekey=no doesn't solve this since SA expiry would be uncoordinated and hence cause packets to be lost. If one side of a Security Tunnel restarts, but doesn't initiate negotiation with its peer, the peer will not be able to communicate with it until the peer thinks the tunnel needs rekeying due to lifetime, or the restarted Security Gateway decides to negotiate for its own reasons. It isn't clear what firewall policies make sense with Opportunism. If VPN and Opportunism connections coexist, security policies implemented via a firewall can only distinguish traffic by IP address.