#!/usr/bin/python # # startvpn: Automatically connect to a VPN when associating with a # wireless network # # Once you've successfully set up an OpenVPN connection in NetworkManager, # configure the settings below, then install this script as # /etc/NetworkManager/dispatcher.d/02startvpn (it seems to be happiest # when chowned root:root) # #-- # Copyright (c) 2008-2009 Bryan Stearns # # Permission is hereby granted, free of charge, to any person obtaining # a copy of this software and associated documentation files (the # "Software"), to deal in the Software without restriction, including # without limitation the rights to use, copy, modify, merge, publish, # distribute, sublicense, and/or sell copies of the Software, and to # permit persons to whom the Software is furnished to do so, subject to # the following conditions: # # The above copyright notice and this permission notice shall be # included in all copies or substantial portions of the Software. # # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. #-- # # Configuration: # # The name of your VPN, as you've set it in Network Manager VPN_NAME = "HomeVPN" # Networks where no VPN is needed (eg, home) PRIVATE_ESSIDS = ["linksys"] # Automatically accept the Personal Telco Project EULA page # for networks with these names: PTP_ESSIDS = ["www.personaltelco.net"] # (If I encounter other oft-hit pages like this, I'll generalize # this mechanism...) # --- that's all --- import sys, os, re, syslog, dbus, httplib, urllib, urlparse, commands from dbus.mainloop.glib import DBusGMainLoop NM_SERVICE="org.freedesktop.NetworkManager" NM_PATH="/org/freedesktop/NetworkManager" NM_VPN_SERVICE ="org.freedesktop.NetworkManager.VPNConnections" NM_VPN_PATH ="/org/freedesktop/NetworkManager/VPNConnections" pid = os.getpid() def log(msg): msg = "%s: %s" % (pid, repr(msg)) print msg syslog.syslog(syslog.LOG_INFO, msg) def doit(): if len(sys.argv) == 3: interface, status = sys.argv[1:3] else: log("Usage: /etc/NetworkManager/dispatcher.d/02startvpn ") sys.exit(0) if status != "up": # log("New status for '%s' is '%s'; ignoring" % (interface, status)) sys.exit(0) iwconfig = commands.getoutput("iwconfig %s" % interface) essid = re.search(r"""ESSID:"(.*?)" """, iwconfig).group(1) log("New wireless network association: '%s'" % essid) if essid in PRIVATE_ESSIDS: log("Not starting VPN: we're home") sys.exit(0) if essid in PTP_ESSIDS: log("Checking for PTP EULAwall") filename, headers = urllib.urlretrieve("http://example.com/index.html") f = open(filename) data = f.read() f.close() # log("Got from GET: '%s'" % data) if data.find("Example Web Page") != -1: log("PTP EULAwall already breached") else: log("Looking for the PTP EULA form") action_match = re.search("form .* action=\"http://(.*)/\"", data) if action_match is None: log("Hmm, doesn't look like the PTP form") sys.exit(0) action = action_match.groups(1)[0] params = urllib.urlencode({'redirect': 'http://example.com', 'mode_login': 'I Agree'}) headers = {"Content-type": "application/x-www-form-urlencoded", "Accept": "text/plain"} conn = httplib.HTTPConnection(action) conn.request("POST", "/", params, headers) response = conn.getresponse() data = response.read() conn.close() log("Got %s / %s from POST" % (response.status, response.reason)) if response.status not in (200, 302): log("Giving up") sys.exit(0) log("Starting '%s' VPN" % VPN_NAME) DBusGMainLoop(set_as_default=True) b = dbus.SystemBus() nm = b.get_object(NM_SERVICE, NM_VPN_PATH, True) interface = dbus.Interface(nm, NM_VPN_SERVICE) result = interface.getVPNConnections() # log(result) # log(interface.getVPNConnectionProperties(VPN_NAME)) def ignore_callback(*args): pass result = interface.activateVPNConnection(VPN_NAME, dbus.Array([], 's'), reply_handler=ignore_callback, error_handler=ignore_callback) # log(result) try: doit() except Exception, e: log("Exception: %s" % e) sys.exit(0)