# vim:syntax=python
from os.path import join as pjoin, dirname as pdirname, \
    basename as pbasename, abspath as pabspath
import sys
from numpy.distutils.misc_util import get_numpy_include_dirs, get_pkg_info

from numscons import GetNumpyEnvironment
from numscons import CheckF77Clib
from SCons.Builder import Builder
from numscons.numdist import process_c_str as process_str


env = GetNumpyEnvironment(ARGUMENTS)
env.Tool('f2py')


#---------------------------
# Builder for generated code
#---------------------------
# Taken from numpy.core.scons_support
# Builder is added where needed (log
def split_ext(string):
    sp = string.rsplit( '.', 1)
    if len(sp) == 1:
        return (sp[0], '')
    else:
        return sp

def do_generate_from_template(targetfile, sourcefile, env):
    t = open(targetfile, 'w')
    s = open(sourcefile, 'r')
    allstr = s.read()
    s.close()
    writestr = process_str(allstr)
    t.write(writestr)
    t.close()
    return 0

def generate_from_template(target, source, env):
    for t, s in zip(target, source):
        do_generate_from_template(str(t), str(s), env)

def generate_from_template_emitter(target, source, env):
    base, ext = split_ext(pbasename(str(source[0])))
    t = pjoin(pdirname(str(target[0])), base)
    return ([t], source)

template_bld = Builder(action = Action(generate_from_template, '$TEMPLATECOMSTR'),
                       emitter = generate_from_template_emitter)
env.Append(BUILDERS = {'GenerateFromTemplate' : template_bld})


if sys.platform=='win32':
#        define_macros.append(('NOINFINITIES',None))
#        define_macros.append(('NONANS',None))
    env.PrependUnique(CPPDEFINES = '_USE_MATH_DEFINES')

config = env.NumpyConfigure(custom_tests = {'CheckF77Clib' : CheckF77Clib})
if not config.CheckF77Clib():
    raise RuntimeError("Could not get C/F77 runtime information")
config.CheckF77Mangling()
config.Finish()

# Note, __file__ undefined, therefore use abspath('.')
env.PrependUnique(CPPPATH=[get_numpy_include_dirs(), env["PYEXTCPPPATH"], 
                           pabspath('.')])
def build_lib(name, ext, libname = None):
    """ext should be .f or .c"""
    if not libname:
        libname = name
    src = env.Glob(pjoin(name, '*%s' % ext))
    assert len(src) > 0
    env.DistutilsStaticExtLibrary(libname, source = src)

# C libraries
build_lib('c_misc', '.c', 'sc_c_misc')
build_lib('cephes', '.c', 'sc_cephes')

# F libraries
# XXX: handle no opt flags for mach
build_lib('mach', '.f', 'sc_mach')
build_lib('amos', '.f', 'sc_amos')
build_lib('cdflib', '.f', 'sc_cdf')
build_lib('specfun', '.f', 'sc_specfunlib')

# Note: cflags only passed to C but not to C++ compiler.  Therefore add npymath
# to _ufuncs_cxx
math_info = get_pkg_info("npymath")
env.MergeFlags(math_info.cflags())
env.MergeFlags(math_info.libs())
env.PrependUnique(LIBPATH = ['.'])

# Ufuncs extension
src = ['_ufuncs.c', 'amos_wrappers.c', 'cdf_wrappers.c', 'specfun_wrappers.c',
       'sf_error.c']
src_logit = env.GenerateFromTemplate('_logit.c.src')
src.extend(src_logit)

src_cxx = ['_ufuncs_cxx.cxx', 'sf_error.c', '_faddeeva.cxx', 'Faddeeva.cc']


env.Prepend(LIBS = ['sc_amos', 'sc_c_misc', 'sc_cephes', 'sc_mach',
                    'sc_cdf', 'sc_specfunlib']) 
env.NumpyPythonExtension('_ufuncs', source = src)

env.NumpyPythonExtension('_ufuncs_cxx', source = src_cxx, 
                         LIBS = ['sc_cephes', 'npymath'])

# Specfun extension
env.Prepend(LIBS = ['sc_specfunlib'])
env.NumpyPythonExtension('specfun', source = 'specfun.pyf',
                         F2PYOPTIONS = ["--no-wrap-functions"])
