#!/usr/bin/env python
import sys,os
import argparse
import pythran
from subprocess import CalledProcessError

parser = argparse.ArgumentParser(prog='pythran',
        description='pythran: a python to C++ compiler',
        epilog="It's a megablast!")
parser.add_argument('input_file', type=str, help='the python module to compile')
parser.add_argument('-o', dest='output_file', type=str, help='path to generated file')
parser.add_argument('-E', dest='translate_only', action='store_true', help='only run the translator, do not compile')
parser.add_argument('-e', dest='raw_translate_only', action='store_true', help='only run the translator, do not generate python glue, do not compile')
parser.add_argument('-f', dest='extra_fflags', metavar='flag', action='append', help='any compiler switch relevant to the underlying C++ compiler', default=list())
parser.add_argument('-m', dest='extra_mflags', metavar='machine', action='append', help='any machine flag relevant to the underlying C++ compiler', default=list())
parser.add_argument('-I', dest='extra_Iflags', metavar='include_dir', action='append', help='any include dir relevant to the underlying C++ compiler', default=list())
parser.add_argument('-D', dest='extra_Dflags', metavar='macro_definition', action='append', help='any macro definition relevant to the underlying C++ compiler', default=list())
parser.add_argument('-O', dest='extra_Oflags', metavar='level', action='append', help='any optimization level relevant to the underlying C++ compiler', default=list())
parser.add_argument('-g', dest='debug_flag', action='store_true', help='any debug level relevant to the underlying C++ compiler', default=list())


args = parser.parse_args()
if args.raw_translate_only:
    args.translate_only=True


try:
    if not os.path.exists(args.input_file):
        raise ValueError("input file `{0}' not found".format(args.input_file))

    module_name = os.path.splitext(os.path.basename(args.input_file))[0]
    if not args.output_file: # build the output file from the input name
        args.output_file = '{0}.{1}'.format(module_name, 'cpp' if args.translate_only else 'so')

    specs = None if args.raw_translate_only else pythran.spec_parser(args.input_file)
    module = pythran.cxx_generator(module_name, file(args.input_file).read(), specs)
    if args.translate_only : # eventually only generate cpp file
        file(args.output_file,'w').write(str(module.generate()))
    else:
        # build using the forwarded compiler options
        compiler = os.environ.get("CXX","c++")
        extra_cxxflags= os.environ.get("CXXFLAGS","").split()\
                + ['-f{0}'.format(n) for n in args.extra_fflags]\
                + ['-m{0}'.format(n) for n in args.extra_mflags]\
                + ['-I{0}'.format(n) for n in args.extra_Iflags]\
                + ['-D{0}'.format(n) for n in args.extra_Dflags]\
                + ['-O{0}'.format(n) for n in args.extra_Oflags]\
                + (['-g'] if args.debug_flag else [])

        pythran.compile(compiler, module, args.output_file,cxxflags=extra_cxxflags)

except IOError as e:
    print >> sys.stderr, "I've got a bad feeling about this..."
    print >> sys.stderr, "E:", e
    sys.exit(1)
except ValueError as e:
    print >> sys.stderr, "Chair to keyboard interface error"
    print >> sys.stderr, "E:", e
    sys.exit(1)
except SyntaxError as e:
    print >> sys.stderr, "I am in trouble. Your input file does not seem to match Pythran's constraints..."
    print >> sys.stderr, "E:", e
    sys.exit(1)
except CalledProcessError as e:
    print >> sys.stderr, "Leave the vessel! Women and children first!"
    print >> sys.stderr, "C++ compiler failed to compile translated code."
    print >> sys.stderr, "E:", e
except NotImplementedError as e:
    print >> sys.stderr, "MAYDAY, MAYDAY, MAYDAY; pythran compiler; code area out of control"
    print >> sys.stderr, "E: not implemented feature needed, bash the developers"
    raise
except EnvironmentError as e:
    print >> sys.stderr, "By Jove! Your environment does not seem to provide all what we need"
    print >> sys.stderr, "E:", e

# what a great editor!
# vim: ft=python
