From: Tony Mack Date: Wed, 2 Mar 2011 21:26:03 +0000 (-0500) Subject: add support for flash clients using flashpolicy X-Git-Tag: sfa-1.0-15~1^2~2 X-Git-Url: http://git.onelab.eu/?a=commitdiff_plain;h=3c9b4d0e434d536c471d225e01723a61af544cb1;p=sfa.git add support for flash clients using flashpolicy --- diff --git a/config/default_config.xml b/config/default_config.xml index aa8a3482..3eecf98e 100644 --- a/config/default_config.xml +++ b/config/default_config.xml @@ -265,6 +265,31 @@ Thierry Parmentelat + + SFA Flash Policy + The settings that affect the flash policy server that will run + as part of this SFA instance. + + + + Enable Flash Policy Server + false + Allows this local SFA instance to run a + flash policy server. + + + Flash policy config file + /etc/sfa/sfa_flashpolicy_config.xml + The path to where the flash policy config file can be reached. + + + Flash policy port + 843 + The flash policy server port. + + + + diff --git a/flashpolicy/.sfa_flashpolicy.py.swp b/flashpolicy/.sfa_flashpolicy.py.swp new file mode 100644 index 00000000..cf37d73c Binary files /dev/null and b/flashpolicy/.sfa_flashpolicy.py.swp differ diff --git a/flashpolicy/sfa_flashpolicy.py b/flashpolicy/sfa_flashpolicy.py new file mode 100644 index 00000000..8ccdc00e --- /dev/null +++ b/flashpolicy/sfa_flashpolicy.py @@ -0,0 +1,115 @@ +#!/usr/bin/env python +# +# flashpolicyd.py +# Simple socket policy file server for Flash +# +# Usage: flashpolicyd.py [--port=N] --file=FILE +# +# Logs to stderr +# Requires Python 2.5 or later + +from __future__ import with_statement +import os +import sys +import optparse +import socket +import thread +import exceptions +import contextlib + +VERSION = 0.1 + +def daemon(): + """Daemonize the current process.""" + if os.fork() != 0: os._exit(0) + os.setsid() + if os.fork() != 0: os._exit(0) + os.umask(0) + devnull = os.open(os.devnull, os.O_RDWR) + os.dup2(devnull, 0) + # xxx fixme - this is just to make sure that nothing gets stupidly lost - should use devnull + crashlog = os.open('/var/log/sfa_flashpolicy.log', os.O_RDWR | os.O_APPEND | os.O_CREAT, 0644) + os.dup2(crashlog, 1) + os.dup2(crashlog, 2) + +class policy_server(object): + def __init__(self, port, path): + self.port = port + self.path = path + self.policy = self.read_policy(path) + self.log('Listening on port %d\n' % port) + try: + self.sock = socket.socket(socket.AF_INET6, socket.SOCK_STREAM) + except AttributeError: + # AttributeError catches Python built without IPv6 + self.sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) + except socket.error: + # socket.error catches OS with IPv6 disabled + self.sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) + self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) + self.sock.bind(('', port)) + self.sock.listen(5) + def read_policy(self, path): + with file(path, 'rb') as f: + policy = f.read(10001) + if len(policy) > 10000: + raise exceptions.RuntimeError('File probably too large to be a policy file', + path) + if 'cross-domain-policy' not in policy: + raise exceptions.RuntimeError('Not a valid policy file', + path) + return policy + def run(self): + try: + while True: + thread.start_new_thread(self.handle, self.sock.accept()) + except socket.error, e: + self.log('Error accepting connection: %s' % (e[1],)) + def handle(self, conn, addr): + addrstr = '%s:%s' % (addr[0],addr[1]) + try: + self.log('Connection from %s' % (addrstr,)) + with contextlib.closing(conn): + # It's possible that we won't get the entire request in + # a single recv, but very unlikely. + request = conn.recv(1024).strip() + if request != '\0': + self.log('Unrecognized request from %s: %s' % (addrstr, request)) + return + self.log('Valid request received from %s' % (addrstr,)) + conn.sendall(self.policy) + self.log('Sent policy file to %s' % (addrstr,)) + except socket.error, e: + self.log('Error handling connection from %s: %s' % (addrstr, e[1])) + except Exception, e: + self.log('Error handling connection from %s: %s' % (addrstr, e[1])) + def log(self, str): + print >>sys.stderr, str + +def main(): + parser = optparse.OptionParser(usage = '%prog [--port=PORT] --file=FILE', + version='%prog ' + str(VERSION)) + parser.add_option('-p', '--port', dest='port', type=int, default=843, + help='listen on port PORT', metavar='PORT') + parser.add_option('-f', '--file', dest='path', + help='server policy file FILE', metavar='FILE') + parser.add_option("-d", "--daemon", dest="daemon", action="store_true", + help="Run as daemon.", default=False) + opts, args = parser.parse_args() + if args: + parser.error('No arguments are needed. See help.') + if not opts.path: + parser.error('File must be specified. See help.') + + try: + if opts.daemon: + daemon() + policy_server(opts.port, opts.path).run() + except Exception, e: + print >> sys.stderr, e + sys.exit(1) + except KeyboardInterrupt: + pass + +if __name__ == '__main__': + main() diff --git a/flashpolicy/sfa_flashpolicy_config.xml b/flashpolicy/sfa_flashpolicy_config.xml new file mode 100644 index 00000000..757022b0 --- /dev/null +++ b/flashpolicy/sfa_flashpolicy_config.xml @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/setup.py b/setup.py index ffa138e8..87a45297 100755 --- a/setup.py +++ b/setup.py @@ -31,6 +31,7 @@ bins = [ 'sfa/client/sfiDeleteAttribute.py', 'sfatables/sfatables', 'keyconvert/keyconvert.py' + 'flashpolicy/sfa_flashpolicy.py', ] package_dirs = [ @@ -47,6 +48,7 @@ package_dirs = [ 'sfatables', 'sfatables/commands', 'sfatables/processors', + 'flashpolicy', ] @@ -60,6 +62,7 @@ data_files = [('/etc/sfa/', [ 'config/aggregates.xml', 'sfa/trust/sig.xsd', 'sfa/trust/xml.xsd', 'sfa/trust/protogeni-rspec-common.xsd', + 'flash_policy/flashpolicy_config.xml', ]), ('/etc/sfatables/matches/', glob('sfatables/matches/*.xml')), ('/etc/sfatables/targets/', glob('sfatables/targets/*.xml')), diff --git a/sfa.spec b/sfa.spec index 27364039..94904c3c 100644 --- a/sfa.spec +++ b/sfa.spec @@ -70,6 +70,11 @@ Summary: sfatables policy tool for SFA Group: Applications/System Requires: sfa +%package flashpolicy +Summary: SFA support for flash clients +Group: Applications/System +Requires: sfa + %Package tests Summary: unit tests suite for SFA Group: Applications/System @@ -95,6 +100,9 @@ sfatables is a tool for defining access and admission control policies in an SFA network, in much the same way as iptables is for ip networks. This is the command line interface to manage sfatables +%description flashpolicy +This package provides support for adobe flash client applications. + %description tests Provides some binary unit tests in /usr/share/sfa/tests @@ -154,6 +162,10 @@ rm -rf $RPM_BUILD_ROOT %files sfatables %{_bindir}/sfatables +%files flashpolicy +%{_bindir}/sfa_flashpolicy.py +/etc/sfa/flashpolicy_config.xml + %files tests %{_datadir}/sfa/tests diff --git a/sfa/init.d/sfa b/sfa/init.d/sfa index 5e579ee5..e4b8fecd 100755 --- a/sfa/init.d/sfa +++ b/sfa/init.d/sfa @@ -75,6 +75,10 @@ start() { action "SFA SliceMgr" daemon /usr/bin/sfa-server.py -s -d $OPTIONS fi + if [ "$SFA_FLASHPOLICY_ENABLED" -eq 1 ]; then + action "Flash Policy Server" daemon /usr/bin/sfa_flashpolicy.py --file="$SFA_FLASHPOLICY_CONFIG_FILE" --port=$SFA_FLASHPOLICY_PORT -d + fi + RETVAL=$? [ $RETVAL -eq 0 ] && touch /var/lock/subsys/sfa-server.py