#!/usr/bin/python

# -*- coding: iso-8859-1 -*-

## Importando modulos
from optparse import OptionParser
import sys
import re
 
def procesa_fichero(fichero):
	"""
	Procesa "fichero", expande los includes, lee las definiciones de
	variables y hace la sustitución de estas
	"""

	## Añade el fichero a la lista de los procesados
	fich_incluidos.append(fichero)
	
	## Analiza el fichero linea a linea
	for linea in file(fichero):
		
		## Buscar "##include <nombre_fichero>"
		tmp = re.search('^ *##include +"(?P<fich>.*)"',linea)
		
		## ¿Encontrado?
		if tmp <> None:
			## SI -> ¿Include recursivo?
			if fich_incluidos.count(tmp.group('fich')) == 0:
				## NO -> incluir fichero
				procesa_fichero(tmp.group('fich'))
				continue
			else:
				## SI -> Error
				sys.exit(fichero +" -> Intento de incluir " + tmp.group('fich') + " recursivamente.")
				
		## Buscar "##define variable valor"
		tmp = re.search("^ *##define (?P<var>.*) (?P<valor>.*)",linea)

		## ¿Encontrado?
		if tmp <> None:
			if variable.has_key(tmp.group('var')) != 1:
				variable[tmp.group('var')] = tmp.group('valor')
				continue
			else:
				sys.exit(fichero + " -> Variable " + tmp.group('var') + " duplicada.")

		## Buscar "@@variable"
		tmp = re.search(" @@(?P<var>.*) ", linea)

		## ¿Encontrado? 
		if tmp <> None:
			if variable.has_key(tmp.group('var')) == 1:
				print re.sub("@@.* ", variable[tmp.group('var')], linea),
				continue
			else:
				sys.exit(fichero + " -> Variable " + tmp.group('var') + " no definido.")
		
	        ## Si nada de lo anterior funciona linea sin modificar
		print linea,

	## Elimina el nombre del fichero de la lista
	fich_incluidos.remove(fichero)


## ---------------------- P R I N C I P A L   -------------------------

## Crea el parser para los argumentos
parser = OptionParser(usage="usage: %prog [options] file", 
		      version="%prog 0.1")

## Opcion -o/--output en el parser
parser.add_option("-o", "--output", 
		  type="string", dest="fsalida", default="stdout",
		  help="output file", metavar="FILE")

## Analiza la linea de comandos (sys.argv[1:])
(opciones, args) = parser.parse_args()

## ¿mas de 1 argumento o menos?
if len(args) != 1:
	## SI -> Error
	parser.error("incorrect number of arguments")

## Variables a usar - Lista de ficheros incluidos para evitar bucles recursivos
fich_incluidos = []

## Variables a usar - Diccionario de variables definidas y sus valores
variable = {}

## Expande los "include" desde el fichero raiz (args[0])
procesa_fichero(args[0])
