You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by bh...@apache.org on 2017/12/02 15:45:41 UTC
[cloudstack] 08/09: CLOUDSTACK-10013: Fix ipsec VPN configuration
This is an automated email from the ASF dual-hosted git repository.
bhaisaab pushed a commit to branch debian9-systemvmtemplate
in repository https://gitbox.apache.org/repos/asf/cloudstack.git
commit d851cf409dc74c43a1796dd9601022dd8e1fdef7
Author: Rohit Yadav <ro...@shapeblue.com>
AuthorDate: Fri Dec 1 20:58:18 2017 +0530
CLOUDSTACK-10013: Fix ipsec VPN configuration
- Fixes strongswan/ipsec, l2tpd and pppd configs
- Uses auto=route in ipsec configs
- Fixes road-warrior setup
- Fixes site-to-site VPN with automatic connection configuration
- Fixes vpc_vpn tests
Signed-off-by: Rohit Yadav <ro...@shapeblue.com>
---
systemvm/patches/debian/opt/cloud/bin/configure.py | 38 +++++++++++++---------
.../patches/debian/opt/cloud/bin/ipsectunnel.sh | 10 +-----
.../debian/opt/cloud/bin/monitor_service.sh | 2 --
systemvm/patches/vpn/etc/ipsec.d/l2tp.conf | 12 +++----
systemvm/patches/vpn/etc/ppp/options.xl2tpd | 2 --
systemvm/patches/vpn/opt/cloud/bin/vpn_l2tp.sh | 18 +++++-----
test/integration/smoke/test_vpc_vpn.py | 26 +++++++++++----
7 files changed, 55 insertions(+), 53 deletions(-)
diff --git a/systemvm/patches/debian/opt/cloud/bin/configure.py b/systemvm/patches/debian/opt/cloud/bin/configure.py
index 68d1c26..b8a3e02 100755
--- a/systemvm/patches/debian/opt/cloud/bin/configure.py
+++ b/systemvm/patches/debian/opt/cloud/bin/configure.py
@@ -546,10 +546,6 @@ class CsSite2SiteVpn(CsDataBag):
ikepolicy=obj['ike_policy'].replace(';','-')
esppolicy=obj['esp_policy'].replace(';','-')
- pfs='no'
- if 'modp' in esppolicy:
- pfs='yes'
-
if rightpeer in self.confips:
self.confips.remove(rightpeer)
file = CsFile(vpnconffile)
@@ -557,7 +553,6 @@ class CsSite2SiteVpn(CsDataBag):
file.search("conn ", "conn vpn-%s" % rightpeer)
file.addeq(" left=%s" % leftpeer)
file.addeq(" leftsubnet=%s" % obj['local_guest_cidr'])
- file.addeq(" leftnexthop=%s" % obj['local_public_gateway'])
file.addeq(" right=%s" % rightpeer)
file.addeq(" rightsubnet=%s" % peerlist)
file.addeq(" type=tunnel")
@@ -567,9 +562,8 @@ class CsSite2SiteVpn(CsDataBag):
file.addeq(" ikelifetime=%s" % self.convert_sec_to_h(obj['ike_lifetime']))
file.addeq(" esp=%s" % esppolicy)
file.addeq(" lifetime=%s" % self.convert_sec_to_h(obj['esp_lifetime']))
- file.addeq(" pfs=%s" % pfs)
file.addeq(" keyingtries=2")
- file.addeq(" auto=start")
+ file.addeq(" auto=route")
if 'encap' not in obj:
obj['encap']=False
file.addeq(" forceencaps=%s" % CsHelper.bool_to_yn(obj['encap']))
@@ -585,10 +579,20 @@ class CsSite2SiteVpn(CsDataBag):
logging.info("Configured vpn %s %s", leftpeer, rightpeer)
CsHelper.execute("ipsec rereadsecrets")
- # This will load the new config and start the connection when needed since auto=start in the config
+ # This will load the new config
CsHelper.execute("ipsec reload")
os.chmod(vpnsecretsfile, 0400)
+ for i in xrange(3):
+ result = CsHelper.execute('ipsec status vpn-%s | grep "%s"' % (rightpeer, peerlist.split(",", 1)[0]))
+ if len(result) > 0:
+ break
+ time.sleep(1)
+
+ # With 'auto=route', connections are established on an attempt to
+ # communicate over the S2S VPN. This uses ping to initialize the connection.
+ CsHelper.execute("timeout 5 ping -c 3 %s" % (peerlist.split("/", 1)[0].replace(".0", ".1")))
+
def convert_sec_to_h(self, val):
hrs = int(val) / 3600
return "%sh" % hrs
@@ -658,6 +662,7 @@ class CsRemoteAccessVpn(CsDataBag):
self.confips = []
logging.debug(self.dbag)
+
for public_ip in self.dbag:
if public_ip == "id":
continue
@@ -665,12 +670,13 @@ class CsRemoteAccessVpn(CsDataBag):
#Enable remote access vpn
if vpnconfig['create']:
+ shutdownIpsec = False
logging.debug("Enabling remote access vpn on "+ public_ip)
dev = CsHelper.get_device(public_ip)
if dev == "":
- logging.error("Request for ipsec to %s not possible because ip is not configured", public_ip)
- continue
+ logging.error("Request for ipsec to %s not possible because ip is not configured", public_ip)
+ continue
CsHelper.start_if_stopped("ipsec")
self.configure_l2tpIpsec(public_ip, self.dbag[public_ip])
@@ -682,7 +688,6 @@ class CsRemoteAccessVpn(CsDataBag):
CsHelper.execute("ipsec rereadsecrets")
else:
logging.debug("Disabling remote access vpn .....")
- #disable remote access vpn
CsHelper.execute("ipsec down L2TP-PSK")
CsHelper.execute("systemctl stop xl2tpd")
@@ -693,7 +698,6 @@ class CsRemoteAccessVpn(CsDataBag):
xl2tpdconffile="/etc/xl2tpd/xl2tpd.conf"
xl2tpoptionsfile='/etc/ppp/options.xl2tpd'
- file = CsFile(l2tpconffile)
localip=obj['local_ip']
localcidr=obj['local_cidr']
publicIface=obj['public_interface']
@@ -701,13 +705,13 @@ class CsRemoteAccessVpn(CsDataBag):
psk=obj['preshared_key']
#left
- file.addeq(" left=%s" % left)
- file.commit()
-
+ l2tpfile = CsFile(l2tpconffile)
+ l2tpfile.addeq(" left=%s" % left)
+ l2tpfile.commit()
secret = CsFile(vpnsecretfilte)
secret.empty()
- secret.addeq(": PSK \"%s\"" %psk)
+ secret.addeq("%s %%any : PSK \"%s\"" % (left, psk))
secret.commit()
xl2tpdconf = CsFile(xl2tpdconffile)
@@ -730,6 +734,8 @@ class CsRemoteAccessVpn(CsDataBag):
self.fw.append(["", "", "-A INPUT -i %s --dst %s -p udp -m udp --dport 1701 -j ACCEPT" % (publicdev, publicip)])
self.fw.append(["", "", "-A INPUT -i %s -p ah -j ACCEPT" % publicdev])
self.fw.append(["", "", "-A INPUT -i %s -p esp -j ACCEPT" % publicdev])
+ self.fw.append(["", "", "-A OUTPUT -p ah -j ACCEPT"])
+ self.fw.append(["", "", "-A OUTPUT -p esp -j ACCEPT"])
if self.config.is_vpc():
self.fw.append(["", ""," -N VPN_FORWARD"])
diff --git a/systemvm/patches/debian/opt/cloud/bin/ipsectunnel.sh b/systemvm/patches/debian/opt/cloud/bin/ipsectunnel.sh
index 20caec5..c42650f 100755
--- a/systemvm/patches/debian/opt/cloud/bin/ipsectunnel.sh
+++ b/systemvm/patches/debian/opt/cloud/bin/ipsectunnel.sh
@@ -142,7 +142,6 @@ ipsec_tunnel_add() {
sudo echo "conn vpn-$rightpeer" > $vpnconffile &&
sudo echo " left=$leftpeer" >> $vpnconffile &&
sudo echo " leftsubnet=$leftnet" >> $vpnconffile &&
- sudo echo " leftnexthop=$leftnexthop" >> $vpnconffile &&
sudo echo " right=$rightpeer" >> $vpnconffile &&
sudo echo " rightsubnets={$rightnets}" >> $vpnconffile &&
sudo echo " type=tunnel" >> $vpnconffile &&
@@ -152,9 +151,8 @@ ipsec_tunnel_add() {
sudo echo " ikelifetime=${ikelifetime}s" >> $vpnconffile &&
sudo echo " esp=$esppolicy" >> $vpnconffile &&
sudo echo " salifetime=${esplifetime}s" >> $vpnconffile &&
- sudo echo " pfs=$pfs" >> $vpnconffile &&
sudo echo " keyingtries=2" >> $vpnconffile &&
- sudo echo " auto=start" >> $vpnconffile &&
+ sudo echo " auto=route" >> $vpnconffile &&
sudo echo "$leftpeer $rightpeer: PSK \"$secret\"" > $vpnsecretsfile &&
sudo chmod 0400 $vpnsecretsfile
@@ -291,12 +289,6 @@ do
done < /tmp/iflist
rightnets=${rightnets//,/ }
-pfs="no"
-echo "$esppolicy" | grep "modp" > /dev/null
-if [ $? -eq 0 ]
-then
- pfs="yes"
-fi
ret=0
#Firewall ports for one-to-one/static NAT
diff --git a/systemvm/patches/debian/opt/cloud/bin/monitor_service.sh b/systemvm/patches/debian/opt/cloud/bin/monitor_service.sh
index d9d8ec8..e1c7914 100755
--- a/systemvm/patches/debian/opt/cloud/bin/monitor_service.sh
+++ b/systemvm/patches/debian/opt/cloud/bin/monitor_service.sh
@@ -50,8 +50,6 @@ echo $processname >> $configFile
echo $service_name >> $configFile
echo $pidfile >> $configFile
-
-
done
}
diff --git a/systemvm/patches/vpn/etc/ipsec.d/l2tp.conf b/systemvm/patches/vpn/etc/ipsec.d/l2tp.conf
index 1cbfe78..2e211e1 100644
--- a/systemvm/patches/vpn/etc/ipsec.d/l2tp.conf
+++ b/systemvm/patches/vpn/etc/ipsec.d/l2tp.conf
@@ -1,13 +1,9 @@
#ipsec remote access vpn configuration
conn L2TP-PSK
- authby=psk
- pfs=no
+ authby=secret
rekey=no
keyingtries=3
- keyexchange=ikev1
- forceencaps=yes
leftfirewall=yes
- leftnexthop=%defaultroute
type=transport
#
# ----------------------------------------------------------
@@ -19,7 +15,7 @@ conn L2TP-PSK
#
left=172.26.0.151
#
- leftprotoport=17/1701
+ leftprotoport=udp/l2tp
# If you insist on supporting non-updated Windows clients,
# you can use: leftprotoport=17/%any
#
@@ -31,10 +27,10 @@ conn L2TP-PSK
# If you want to allow multiple connections from any IP address,
# you can use: right=%any
#
- rightprotoport=17/%any
+ rightprotoport=udp/%any
#
# ----------------------------------------------------------
# Change 'ignore' to 'add' to enable this configuration.
#
rightsubnetwithin=0.0.0.0/0
- auto=add
+ auto=route
diff --git a/systemvm/patches/vpn/etc/ppp/options.xl2tpd b/systemvm/patches/vpn/etc/ppp/options.xl2tpd
index 08c301b..a01687f 100644
--- a/systemvm/patches/vpn/etc/ppp/options.xl2tpd
+++ b/systemvm/patches/vpn/etc/ppp/options.xl2tpd
@@ -4,11 +4,9 @@ ipcp-accept-remote
noccp
idle 1800
auth
-crtscts
mtu 1410
mru 1410
nodefaultroute
debug
-lock
connect-delay 5000
ms-dns 10.1.1.1
diff --git a/systemvm/patches/vpn/opt/cloud/bin/vpn_l2tp.sh b/systemvm/patches/vpn/opt/cloud/bin/vpn_l2tp.sh
index 60ee8a6..5928548 100755
--- a/systemvm/patches/vpn/opt/cloud/bin/vpn_l2tp.sh
+++ b/systemvm/patches/vpn/opt/cloud/bin/vpn_l2tp.sh
@@ -87,15 +87,15 @@ iptables_() {
}
start_ipsec() {
- service ipsec status > /dev/null
+ systemctl is-active ipsec > /dev/null
if [ $? -ne 0 ]
then
- service ipsec start > /dev/null
+ systemctl start ipsec > /dev/null
#Wait until ipsec started, 5 seconds at most
for i in {1..5}
do
logger -t cloud "$(basename $0): waiting ipsec start..."
- service ipsec status > /dev/null
+ systemctl is-active ipsec > /dev/null
result=$?
if [ $result -eq 0 ]
then
@@ -104,7 +104,7 @@ start_ipsec() {
sleep 1
done
fi
- service ipsec status > /dev/null
+ systemctl is-active ipsec > /dev/null
return $?
}
@@ -112,14 +112,14 @@ ipsec_server() {
local op=$1
case $op in
"start") start_ipsec
- sudo service xl2tpd start
+ sudo systemctl start xl2tpd
;;
- "stop") sudo service xl2tpd stop
+ "stop") sudo systemctl stop xl2tpd
;;
"restart") start_ipsec
sudo ipsec auto --rereadall
- service xl2tpd stop
- service xl2tpd start
+ systemctl stop xl2tpd
+ systemctl start xl2tpd
;;
esac
}
@@ -131,7 +131,7 @@ create_l2tp_ipsec_vpn_server() {
local local_ip=$4
sed -i -e "s/left=.*$/left=$public_ip/" /etc/ipsec.d/l2tp.conf
- echo ": PSK \"$ipsec_psk\"" > /etc/ipsec.d/ipsec.any.secrets
+ echo "$public_ip %any : PSK \"$ipsec_psk\"" > /etc/ipsec.d/ipsec.any.secrets
sed -i -e "s/^ip range = .*$/ip range = $client_range/" /etc/xl2tpd/xl2tpd.conf
sed -i -e "s/^local ip = .*$/local ip = $local_ip/" /etc/xl2tpd/xl2tpd.conf
diff --git a/test/integration/smoke/test_vpc_vpn.py b/test/integration/smoke/test_vpc_vpn.py
index ddf7693..83c244b 100644
--- a/test/integration/smoke/test_vpc_vpn.py
+++ b/test/integration/smoke/test_vpc_vpn.py
@@ -21,7 +21,8 @@ from marvin.codes import PASS, FAILED
from marvin.cloudstackTestCase import cloudstackTestCase
from marvin.lib.utils import (validateList,
cleanup_resources,
- get_process_status)
+ get_process_status,
+ wait_until)
from marvin.lib.base import (Domain,
Account,
@@ -184,7 +185,7 @@ class Services:
},
"vpn": {
"vpn_user": "root",
- "vpn_pass": "Md1s#dc",
+ "vpn_pass": "Md1sdc",
"vpn_pass_fail": "abc!123", # too short
"iprange": "10.3.2.1-10.3.2.10",
"fordisplay": "true"
@@ -756,8 +757,19 @@ class TestVpcSite2SiteVpn(cloudstackTestCase):
self.apiclient, customer2_response.id, vpn1_response['id'])
self.debug("VPN connection created for VPC %s" % vpc1.id)
- self.assertEqual(
- vpnconn2_response['state'], "Connected", "Failed to connect between VPCs!")
+ def checkVpnConnected():
+ connections = Vpn.listVpnConnection(
+ self.apiclient,
+ listall='true',
+ vpcid=vpc2.id)
+ if isinstance(connections, list):
+ return connections[0].state == 'Connected', None
+ return False, None
+
+ # Wait up to 60 seconds for passive connection to show up as Connected
+ res, _ = wait_until(2, 30, checkVpnConnected)
+ if not res:
+ self.fail("Failed to connect between VPCs, see VPN state as Connected")
# acquire an extra ip address to use to ssh into vm2
try:
@@ -792,9 +804,9 @@ class TestVpcSite2SiteVpn(cloudstackTestCase):
if ssh_client:
# run ping test
- packet_loss = ssh_client.execute(
- "/bin/ping -c 3 -t 10 " + vm1.nic[0].ipaddress + " |grep packet|cut -d ' ' -f 7| cut -f1 -d'%'")[0]
- self.assert_(int(packet_loss) == 0, "Ping did not succeed")
+ packet_loss = ssh_client.execute("/bin/ping -c 3 -t 10 " + vm1.nic[0].ipaddress + " | grep packet | sed 's/.*received, //g' | sed 's/[% ]*packet.*//g'")[0]
+ # during startup, some packets may not reply due to link/ipsec-route setup
+ self.assert_(int(packet_loss) < 50, "Ping did not succeed")
else:
self.fail("Failed to setup ssh connection to %s" % vm2.public_ip)
--
To stop receiving notification emails like this one, please contact
"commits@cloudstack.apache.org" <co...@cloudstack.apache.org>.