Chris PeBenito 17de1b7
#!/usr/bin/python
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
#  Author(s): Donald Miner <dminer@tresys.com>
Chris PeBenito 17de1b7
#             Dave Sugar <dsugar@tresys.com>
Chris PeBenito 17de1b7
#             Brian Williams <bwilliams@tresys.com>
Chris PeBenito 17de1b7
#
Chris PeBenito 17de1b7
# Copyright (C) 2005 - 2006 Tresys Technology, LLC
Chris PeBenito 17de1b7
#      This program is free software; you can redistribute it and/or modify
Chris PeBenito 17de1b7
#      it under the terms of the GNU General Public License as published by
Chris PeBenito 17de1b7
#      the Free Software Foundation, version 2.
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
"""
Chris PeBenito 17de1b7
	This script generates XML documentation information for layers specified
Chris PeBenito 17de1b7
	by the user.
Chris PeBenito 17de1b7
"""
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
import sys
Chris PeBenito 17de1b7
import os
Chris PeBenito 17de1b7
import glob
Chris PeBenito 17de1b7
import re
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# GLOBALS
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Default values of command line arguments:
Chris PeBenito 17de1b7
warn = False
Chris PeBenito 17de1b7
meta = "metadata"
Chris PeBenito 17de1b7
third_party = "third-party"
Chris PeBenito 17de1b7
layers = {}
Chris PeBenito 17de1b7
tunable_files = []
Chris PeBenito 17de1b7
bool_files = []
Chris PeBenito 17de1b7
xml_tunable_files = []
Chris PeBenito 17de1b7
xml_bool_files = []
Chris PeBenito 17de1b7
output_dir = ""
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Pre compiled regular expressions:
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Matches either an interface or a template declaration. Will give the tuple:
Chris PeBenito 17de1b7
#	("interface" or "template", name)
Chris PeBenito 17de1b7
# Some examples:
Chris PeBenito 17de1b7
#	"interface(`kernel_read_system_state',`"
Chris PeBenito 17de1b7
#	 -> ("interface", "kernel_read_system_state")
Chris PeBenito 17de1b7
#	"template(`base_user_template',`"
Chris PeBenito 17de1b7
#	 -> ("template", "base_user_template")
Chris PeBenito 17de1b7
INTERFACE = re.compile("^\s*(interface|template)\(`(\w*)'")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Matches either a gen_bool or a gen_tunable statement. Will give the tuple:
Chris PeBenito 17de1b7
#	("tunable" or "bool", name, "true" or "false")
Chris PeBenito 17de1b7
# Some examples:
Chris PeBenito 17de1b7
#	"gen_bool(secure_mode, false)"
Chris PeBenito 17de1b7
#	 -> ("bool", "secure_mode", "false")
Chris PeBenito 17de1b7
#	"gen_tunable(allow_kerberos, false)"
Chris PeBenito 17de1b7
#	 -> ("tunable", "allow_kerberos", "false")
Chris PeBenito 17de1b7
BOOLEAN = re.compile("^\s*gen_(tunable|bool)\(\s*(\w*)\s*,\s*(true|false)\s*\)")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Matches a XML comment in the policy, which is defined as any line starting
Chris PeBenito 17de1b7
#  with two # and at least one character of white space. Will give the single
Chris PeBenito 17de1b7
#  valued tuple:
Chris PeBenito 17de1b7
#	("comment")
Chris PeBenito 17de1b7
# Some Examples:
Chris PeBenito 17de1b7
#	"## <summary>"
Chris PeBenito 17de1b7
#	 -> ("<summary>")
Chris PeBenito 17de1b7
#	"##		The domain allowed access.	"
Chris PeBenito 17de1b7
#	 -> ("The domain allowed access.")
Chris PeBenito 17de1b7
XML_COMMENT = re.compile("^##\s+(.*?)\s*$")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# FUNCTIONS
Chris PeBenito 17de1b7
def getModuleXML(file_name):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Returns the XML data for a module in a list, one line per list item.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Try to open the file, if it cant, just ignore it.
Chris PeBenito 17de1b7
	try:
Chris PeBenito 17de1b7
		module_file = open(file_name, "r")
Chris PeBenito 17de1b7
		module_code = module_file.readlines()
Chris PeBenito 17de1b7
		module_file.close()
Chris PeBenito 17de1b7
	except:
Chris PeBenito 17de1b7
		warning("cannot open file %s for read, skipping" % file_name)
Chris PeBenito 17de1b7
		return []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	module_buf = []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Infer the module name, which is the base of the file name.
Chris PeBenito 17de1b7
	module_buf.append("<module name=\"%s\" filename=\"%s\">\n" 
Chris PeBenito 17de1b7
		% (os.path.splitext(os.path.split(file_name)[-1])[0], file_name))
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	temp_buf = []
Chris PeBenito 17de1b7
	interface = None
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# finding_header is a flag to denote whether we are still looking
Chris PeBenito 17de1b7
	#  for the XML documentation at the head of the file.
Chris PeBenito 17de1b7
	finding_header = True
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Get rid of whitespace at top of file
Chris PeBenito 17de1b7
	while(module_code and module_code[0].isspace()):
Chris PeBenito 17de1b7
		module_code = module_code[1:]
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Go line by line and figure out what to do with it.
Chris PeBenito 17de1b7
	line_num = 0
Chris PeBenito 17de1b7
	for line in module_code:
Chris PeBenito 17de1b7
		line_num += 1
Chris PeBenito 17de1b7
		if finding_header:
Chris PeBenito 17de1b7
			# If there is a XML comment, add it to the temp buffer.
Chris PeBenito 17de1b7
			comment = XML_COMMENT.match(line)
Chris PeBenito 17de1b7
			if comment:
Chris PeBenito 17de1b7
				temp_buf.append(comment.group(1) + "\n")
Chris PeBenito 17de1b7
				continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			# Once a line that is not an XML comment is reached,
Chris PeBenito 17de1b7
			#  either put the XML out to module buffer as the
Chris PeBenito 17de1b7
			#  module's documentation, or attribute it to an
Chris PeBenito 17de1b7
			#  interface/template.
Chris PeBenito 17de1b7
			elif temp_buf:
Chris PeBenito 17de1b7
				finding_header = False
Chris PeBenito 17de1b7
				interface = INTERFACE.match(line)
Chris PeBenito 17de1b7
				if not interface:
Chris PeBenito 17de1b7
					module_buf += temp_buf
Chris PeBenito 17de1b7
					temp_buf = []
Chris PeBenito 17de1b7
					continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		# Skip over empty lines
Chris PeBenito 17de1b7
		if line.isspace():
Chris PeBenito 17de1b7
			continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		# Grab a comment and add it to the temprorary buffer, if it
Chris PeBenito 17de1b7
		#  is there.
Chris PeBenito 17de1b7
		comment = XML_COMMENT.match(line)
Chris PeBenito 17de1b7
		if comment:
Chris PeBenito 17de1b7
			temp_buf.append(comment.group(1) + "\n")
Chris PeBenito 17de1b7
			continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		# Grab the interface information. This is only not true when
Chris PeBenito 17de1b7
		#  the interface is at the top of the file and there is no
Chris PeBenito 17de1b7
		#  documentation for the module.
Chris PeBenito 17de1b7
		if not interface:
Chris PeBenito 17de1b7
			interface = INTERFACE.match(line)
Chris PeBenito 17de1b7
		if interface:
Chris PeBenito 17de1b7
			# Add the opening tag for the interface/template
Chris PeBenito 17de1b7
			groups = interface.groups()
Chris PeBenito 17de1b7
			module_buf.append("<%s name=\"%s\" lineno=\"%s\">\n" % (groups[0], groups[1], line_num))
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			# Add all the comments attributed to this interface to
Chris PeBenito 17de1b7
			#  the module buffer.
Chris PeBenito 17de1b7
			if temp_buf:
Chris PeBenito 17de1b7
				module_buf += temp_buf
Chris PeBenito 17de1b7
				temp_buf = []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			# Add default summaries and parameters so that the
Chris PeBenito 17de1b7
			#  DTD is happy.
Chris PeBenito 17de1b7
			else:
Chris PeBenito 17de1b7
				warning ("unable to find XML for %s %s()" % (groups[0], groups[1]))	
Chris PeBenito 17de1b7
				module_buf.append("<summary>\n")
Chris PeBenito 17de1b7
				module_buf.append("Summary is missing!\n")
Chris PeBenito 17de1b7
				module_buf.append("</summary>\n")
Chris PeBenito 17de1b7
				module_buf.append("<param name=\"?\">\n")
Chris PeBenito 17de1b7
				module_buf.append("<summary>\n")
Chris PeBenito 17de1b7
				module_buf.append("Parameter descriptions are missing!\n")
Chris PeBenito 17de1b7
				module_buf.append("</summary>\n")
Chris PeBenito 17de1b7
				module_buf.append("</param>\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			# Close the interface/template tag.
Chris PeBenito 17de1b7
			module_buf.append("</%s>\n" % interface.group(1))
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			interface = None
Chris PeBenito 17de1b7
			continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# If the file just had a header, add the comments to the module buffer.
Chris PeBenito 17de1b7
	if finding_header:
Chris PeBenito 17de1b7
		module_buf += temp_buf
Chris PeBenito 17de1b7
	# Otherwise there are some lingering XML comments at the bottom, warn
Chris PeBenito 17de1b7
	#  the user.
Chris PeBenito 17de1b7
	elif temp_buf:
Chris PeBenito 17de1b7
		warning("orphan XML comments at bottom of file %s" % file_name)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	module_buf.append("</module>\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	return module_buf
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def getLayerXML (layerName, directories):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Returns the XML documentation for a layer.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	layer_buf = []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Infer the layer name from the directory name.
Chris PeBenito 17de1b7
	layer_buf.append("<layer name=\"%s\">\n" % layerName)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Try to file the metadata file for this layer and if it exists,
Chris PeBenito 17de1b7
	# append the contents to the buffer.
Chris PeBenito 17de1b7
	bFoundMeta = False
Chris PeBenito 17de1b7
	for directory in directories:
Chris PeBenito 17de1b7
		metafile = directory + "/" + meta
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		if not bFoundMeta and os.path.isfile (metafile):
Chris PeBenito 17de1b7
			layer_meta = open (metafile, "r")
Chris PeBenito 17de1b7
			layer_buf += layer_meta.readlines ()
Chris PeBenito 17de1b7
			layer_meta.close()
Chris PeBenito 17de1b7
			bFoundMeta = True
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# force the metadata for the third party layer
Chris PeBenito 17de1b7
	if not bFoundMeta:
Chris PeBenito 17de1b7
		if layerName == third_party:
Chris PeBenito 17de1b7
			layer_buf.append ("<summary>This is all third-party generated modules.</summary>\n")
Chris PeBenito 17de1b7
			bFoundMeta = True
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# didn't find meta data for this layer - oh well	
Chris PeBenito 17de1b7
	if not bFoundMeta:
Chris PeBenito 17de1b7
		layer_buf.append ("<summary>Summary is missing!.</summary>\n")
Chris PeBenito 17de1b7
		warning ("unable to find %s for layer %s" % (meta, layerName))	
Chris PeBenito 17de1b7
	
Chris PeBenito 17de1b7
	# For each module file in the layer, add its XML.
Chris PeBenito 17de1b7
	for directory in directories:
Chris PeBenito 17de1b7
		modules = glob.glob("%s/*.if" % directory)
Chris PeBenito 17de1b7
		modules.sort()
Chris PeBenito 17de1b7
		for module in modules:
Chris PeBenito 17de1b7
			layer_buf += getModuleXML(module)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	layer_buf.append("</layer>\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	return layer_buf
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def getTunableXML(file_name, kind):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Return all the XML for the tunables/bools in the file specified.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Try to open the file, if it cant, just ignore it.
Chris PeBenito 17de1b7
	try:
Chris PeBenito 17de1b7
		tunable_file = open(file_name, "r")
Chris PeBenito 17de1b7
		tunable_code = tunable_file.readlines()
Chris PeBenito 17de1b7
		tunable_file.close()
Chris PeBenito 17de1b7
	except:
Chris PeBenito 17de1b7
		warning("cannot open file %s for read, skipping" % file_name)
Chris PeBenito 17de1b7
		return []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	tunable_buf = []
Chris PeBenito 17de1b7
	temp_buf = []
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Find tunables and booleans line by line and use the comments above
Chris PeBenito 17de1b7
	# them.
Chris PeBenito 17de1b7
	for line in tunable_code:
Chris PeBenito 17de1b7
		# If it is an XML comment, add it to the buffer and go on.
Chris PeBenito 17de1b7
		comment = XML_COMMENT.match(line)
Chris PeBenito 17de1b7
		if comment:
Chris PeBenito 17de1b7
			temp_buf.append(comment.group(1) + "\n")
Chris PeBenito 17de1b7
			continue
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		# Get the boolean/tunable data.
Chris PeBenito 17de1b7
		boolean = BOOLEAN.match(line)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		# If we reach a boolean/tunable declaration, attribute all XML
Chris PeBenito 17de1b7
		#  in the temp buffer to it and add XML to the tunable buffer.
Chris PeBenito 17de1b7
		if boolean:
Chris PeBenito 17de1b7
			# If there is a gen_bool in a tunable file or a
Chris PeBenito 17de1b7
			# gen_tunable in a boolean file, error and exit.
Chris PeBenito 17de1b7
			if boolean.group(1) != kind:
Chris PeBenito 17de1b7
				error("%s in a %s file." % (boolean.group(1), kind))
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
			tunable_buf.append("<%s name=\"%s\" dftval=\"%s\">\n" % boolean.groups())
Chris PeBenito 17de1b7
			tunable_buf += temp_buf
Chris PeBenito 17de1b7
			temp_buf = []
Chris PeBenito 17de1b7
			tunable_buf.append("</%s>\n" % boolean.group(1))
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# If there are XML comments at the end of the file, they arn't
Chris PeBenito 17de1b7
	# attributed to anything. These are ignored.
Chris PeBenito 17de1b7
	if len(temp_buf):
Chris PeBenito 17de1b7
		warning("orphan XML comments at bottom of file %s" % file_name)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# If the caller requested a the global_tunables and global_booleans to be
Chris PeBenito 17de1b7
	# output to a file output them now
Chris PeBenito 17de1b7
	if len(output_dir) > 0:
Chris PeBenito 17de1b7
		xmlfile = os.path.split(file_name)[1] + ".xml"
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
		try:
Chris PeBenito 17de1b7
			xml_outfile = open(output_dir + "/" + xmlfile, "w")
Chris PeBenito 17de1b7
			for tunable_line in tunable_buf:
Chris PeBenito 17de1b7
				xml_outfile.write (tunable_line)
Chris PeBenito 17de1b7
			xml_outfile.close()
Chris PeBenito 17de1b7
		except:
Chris PeBenito 17de1b7
			warning ("cannot write to file %s, skipping creation" % xmlfile)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	return tunable_buf
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def getXMLFileContents (file_name):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Return all the XML in the file specified.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	tunable_buf = []
Chris PeBenito 17de1b7
	# Try to open the xml file for this type of file
Chris PeBenito 17de1b7
	# append the contents to the buffer.
Chris PeBenito 17de1b7
	try:
Chris PeBenito 17de1b7
		tunable_xml = open(file_name, "r")
Chris PeBenito 17de1b7
		tunable_buf += tunable_xml.readlines()
Chris PeBenito 17de1b7
		tunable_xml.close()
Chris PeBenito 17de1b7
	except:
Chris PeBenito 17de1b7
		warning("cannot open file %s for read, assuming no data" % file_name)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	return tunable_buf
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def getPolicyXML():
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Return the compelete reference policy XML documentation through a list,
Chris PeBenito 17de1b7
	one line per item.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	policy_buf = []
Chris PeBenito 17de1b7
	policy_buf.append("<policy>\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Add to the XML each layer specified by the user.
Chris PeBenito 17de1b7
	for layer in layers.keys ():
Chris PeBenito 17de1b7
		policy_buf += getLayerXML(layer, layers[layer])
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Add to the XML each tunable file specified by the user.
Chris PeBenito 17de1b7
	for tunable_file in tunable_files:
Chris PeBenito 17de1b7
		policy_buf += getTunableXML(tunable_file, "tunable")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Add to the XML each XML tunable file specified by the user.
Chris PeBenito 17de1b7
	for tunable_file in xml_tunable_files:
Chris PeBenito 17de1b7
		policy_buf += getXMLFileContents (tunable_file)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Add to the XML each bool file specified by the user.
Chris PeBenito 17de1b7
	for bool_file in bool_files:
Chris PeBenito 17de1b7
		policy_buf += getTunableXML(bool_file, "bool")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	# Add to the XML each XML bool file specified by the user.
Chris PeBenito 17de1b7
	for bool_file in xml_bool_files:
Chris PeBenito 17de1b7
		policy_buf += getXMLFileContents (bool_file)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	policy_buf.append("</policy>\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	return policy_buf
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def usage():
Chris PeBenito 17de1b7
	"""
Chris PeBenito 17de1b7
	Displays a message describing the proper usage of this script.
Chris PeBenito 17de1b7
	"""
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("usage: %s [-w] [-m file] "\
Chris PeBenito 17de1b7
		% sys.argv[0])
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("layerdirectory [layerdirectory...]\n\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("Options:\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write ("-h --help                      -- "+\
Chris PeBenito 17de1b7
				"show command line options\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("-w --warn                      -- "+\
Chris PeBenito 17de1b7
				"show warnings\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("-m --meta <file>               -- "+\
Chris PeBenito 17de1b7
				"the filename of the metadata in each layer\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("-t --tunable <file>            -- "+\
Chris PeBenito 17de1b7
				"A file containing tunable declarations\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("-b --bool <file>               -- "+\
Chris PeBenito 17de1b7
				"A file containing bool declarations\n")
Chris PeBenito 17de1b7
												   
Chris PeBenito 17de1b7
	sys.stdout.write("-o --output-dir <directory>    -- "+\
Chris PeBenito 17de1b7
				"A directory to output global_tunables.xml and global_booleans.xml\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("--tunables-xml <file>          -- "+\
Chris PeBenito 17de1b7
				"A file containing tunable declarations already in XML format\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stdout.write("--booleans-xml <file>          -- "+\
Chris PeBenito 17de1b7
				"A file containing bool declarations already in XML format\n")
Chris PeBenito 17de1b7
				
Chris PeBenito 17de1b7
	sys.stdout.write ("-3 --third-party <directory>   -- "+\
Chris PeBenito 17de1b7
				"Look for 3rd Party modules in directory.\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def warning(description):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Warns the user of a non-critical error.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	if warn:
Chris PeBenito 17de1b7
		sys.stderr.write("%s: " % sys.argv[0] )
Chris PeBenito 17de1b7
		sys.stderr.write("warning: " + description + "\n")
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
def error(description):
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
	Describes an error and exists the program.
Chris PeBenito 17de1b7
	'''
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	sys.stderr.write("%s: " % sys.argv[0] )
Chris PeBenito 17de1b7
        sys.stderr.write("error: " + description + "\n")
Chris PeBenito 17de1b7
        sys.stderr.flush()
Chris PeBenito 17de1b7
        sys.exit(1)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# MAIN PROGRAM
Chris PeBenito 17de1b7
# Check that there are command line arguments.
Chris PeBenito 17de1b7
if len(sys.argv) <= 1:
Chris PeBenito 17de1b7
	usage()
Chris PeBenito 17de1b7
	sys.exit(1)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Parse the command line arguments
Chris PeBenito 17de1b7
for i in range(1, len(sys.argv)):
Chris PeBenito 17de1b7
	if sys.argv[i-1] in ("-m", "--meta",\
Chris PeBenito 17de1b7
					"-t", "--tunable", "-b", "--bool",\
Chris PeBenito 17de1b7
					"-o", "--output-dir", "-3", "--third-party", \
Chris PeBenito 17de1b7
					"--tunables-xml", "--booleans-xml"):
Chris PeBenito 17de1b7
		continue
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-w", "--warn"):
Chris PeBenito 17de1b7
		warn = True
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-m", "--meta"):
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			meta = sys.argv[i+1]
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage()
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-t", "--tunable"):
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			tunable_files.append(sys.argv[i+1])
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage()
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-b", "--bool"):
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			bool_files.append(sys.argv[i+1])
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage()
Chris PeBenito 17de1b7
	
Chris PeBenito 17de1b7
	elif sys.argv[i] == "--tunables-xml":
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			xml_bool_files.append (sys.argv[i+1])
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage ()
Chris PeBenito 17de1b7
			
Chris PeBenito 17de1b7
	elif sys.argv[i] == "--booleans-xml":
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			xml_tunable_files.append (sys.argv[i+1])
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage ()
Chris PeBenito 17de1b7
			
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-o", "--output-dir"):
Chris PeBenito 17de1b7
		if i < len(sys.argv)-1:
Chris PeBenito 17de1b7
			output_dir = sys.argv[i+1]
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage ()
Chris PeBenito 17de1b7
			
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-3", "--third-party"):
Chris PeBenito 17de1b7
		if i < len(sys.argv) -1:
Chris PeBenito 17de1b7
			if layers.has_key (third_party):
Chris PeBenito 17de1b7
				layers[third_party].append (sys.argv[i+1])
Chris PeBenito 17de1b7
			else:
Chris PeBenito 17de1b7
				layers[third_party] = [sys.argv[i+1]]
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			usage ()
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	elif sys.argv[i] in ("-h", "--help"):
Chris PeBenito 17de1b7
		usage ()
Chris PeBenito 17de1b7
		sys.exit (1)
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
	else:
Chris PeBenito 17de1b7
		# store directories in hash stored by layer name
Chris PeBenito 17de1b7
		splitlayer = os.path.split(sys.argv[i])
Chris PeBenito 17de1b7
		if layers.has_key (splitlayer[1]):
Chris PeBenito 17de1b7
			layers[splitlayer[1]].append (sys.argv[i])
Chris PeBenito 17de1b7
		else:
Chris PeBenito 17de1b7
			layers[splitlayer[1]] = [sys.argv[i]]
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
Chris PeBenito 17de1b7
# Generate the XML and output it to a file
Chris PeBenito 17de1b7
lines = getPolicyXML()
Chris PeBenito 17de1b7
for s in lines:
Chris PeBenito 17de1b7
	sys.stdout.write(s)
Chris PeBenito 17de1b7